h/m/customs: migration from isc-dhcp4 to kea

Kea configuration added in its own file for general cleanness.
Migrated only lan and bms subnets; others appear to be legacy leftovers.
IP reservations migrated as-is; "one-liner" for that in comments.
Hopefully legacy "bootp" is not actually needed as that's behind a
paywall.
Generated config tested using `kea-dhcp4 -tT -c ./generated/dhcp4.conf`
Drive-by fix for checkinator to keep it working with old config with no
DHCP_SERVER config key.
Added myself to OWNERS as I'm making frequent changes here recently, and
vuko is absent.

Change-Id: I5d5dd71ab4fd3fb498bd8bc95428984b3b08f092
Reviewed-on: https://gerrit.hackerspace.pl/c/hscloud/+/1943
Reviewed-by: q3k <q3k@hackerspace.pl>
Reviewed-by: informatic <informatic@hackerspace.pl>
changes/43/1943/16
ar 2024-03-20 17:14:06 +01:00 committed by ar
parent 1bcaa97d87
commit aa4b72e50e
6 changed files with 146 additions and 226 deletions

View File

@ -78,10 +78,13 @@ def server():
args = parser.parse_args()
config = yaml.safe_load(args.config.read_text())
if config['DHCP_SERVER'] == "kea":
tracker = KeaUpdater(config['KEA_LEASE_FILE'], config['TIMEOUT'])
elif config['DHCP_SERVER'] == "isc" or "DHCP_SERVER" not in config:
server = config.get('DHCP_SERVER', 'isc')
if server == 'isc':
tracker = DhcpdUpdater(config['LEASE_FILE'], config['TIMEOUT'])
elif server == 'kea':
tracker = KeaUpdater(config['KEA_LEASE_FILE'], config['TIMEOUT'])
else:
raise Exception('invalid DHCP_SERVER value, expected isc or kea')
tracker.start()
server = grpc.server(futures.ThreadPoolExecutor(max_workers=10))

View File

@ -2,3 +2,4 @@ inherited: false
owners:
- informatic
- vuko
- ar

View File

@ -25,6 +25,8 @@ let
config = builtins.toFile "${name}-config.yaml" (pkgs.lib.generators.toYAML {} {
# path to dhcpd lease file
LEASE_FILE = "/var/lib/dhcpd4/dhcpd.leases";
KEA_LEASE_FILE = "/var/lib/kea/dhcp4.leases";
DHCP_SERVER = "kea";
# timeout for old leases
TIMEOUT = 1500;

View File

@ -56,6 +56,7 @@ in {
./doorman/service.nix
./beyondspace.nix
./laserproxy/service.nix
./kea.nix
];
# Prevent spurious rebuilds due to dbus override on minimal profile
@ -332,12 +333,6 @@ in {
users.users.root.openssh.authorizedKeys.keys = [ vuko-pubkey q3k-pubkey ];
services.dhcpd4 = {
enable = true;
configFile = "${./dhcpd.conf}";
interfaces = ["lan" "bms"];
};
services.mosquitto.enable = true;
services.mosquitto.listeners = [
{
@ -352,16 +347,6 @@ in {
}
];
# Checkinator needs access to leases file. When DynamicUser is enable this
# file is hidden in /var/lib/private
systemd.services.dhcpd4.serviceConfig.DynamicUser= pkgs.lib.mkForce false;
users.users.dhcpd = {
group = "dhcpd";
isSystemUser = true;
uid = 1005;
};
users.groups."dhcpd" = {};
hscloud.routing = {
enable = true;
# TODO(q3k): make this optional in upstream

View File

@ -1,207 +0,0 @@
option domain-search "waw.hackerspace.pl";
option domain-name-servers 10.8.1.2;
default-lease-time 600;
max-lease-time 600;
one-lease-per-client true;
option cisco-ip-phone-tftp code 150 = ip-address;
subnet 10.8.0.0 netmask 255.255.0.0 {
option routers 10.8.1.2;
range 10.8.0.20 10.8.0.199;
authoritative;
allow bootp;
if substring (option vendor-class-identifier, 15, 5) = "00000" {
filename "netboot.xyz.kpxe";
} else {
filename "netboot.xyz.efi";
}
next-server 10.8.1.2;
host laser {
hardware ethernet 00:0e:35:1d:a1:a4;
fixed-address 10.8.1.18;
}
host oki {
hardware ethernet 00:25:36:de:27:56;
fixed-address 10.8.1.20;
}
host brother {
hardware ethernet 00:1b:a9:24:96:e2;
fixed-address 10.8.1.21;
}
host zebra {
hardware ethernet 00:07:4d:4d:71:e4;
fixed-address 10.8.1.22;
}
host lj2100 {
hardware ethernet 00:30:C1:62:61:23;
fixed-address 10.8.1.23;
}
host dht21 {
hardware ethernet 5c:cf:7f:06:9a:3e;
fixed-address 10.8.1.25;
}
host ledpanel {
hardware ethernet 00:0A:35:00:01:22;
fixed-address 10.8.1.26;
}
host printmaster {
hardware ethernet b8:27:eb:ed:df:f9;
fixed-address 10.8.1.17;
}
host bridgeport {
hardware ethernet 90:1b:0e:1d:23:09;
fixed-address 10.8.1.29;
}
host 3printers1cups {
hardware ethernet 02:20:f5:20:6a:2d;
fixed-address 10.8.1.30;
}
host telelele {
hardware ethernet fe:77:d6:83:26:b1;
fixed-address 10.8.1.31;
}
# vending
host vending {
#hardware ethernet b8:27:eb:71:e4:0e;
#hardware ethernet b8:27:eb:3d:ba:fe;
hardware ethernet b8:27:eb:03:69:01;
fixed-address 10.8.1.32;
}
host transcend {
hardware ethernet b0:38:29:2e:5d:c9;
fixed-address 10.8.1.33;
}
host welcomer {
hardware ethernet b8:27:eb:37:9e:6e;
fixed-address 10.8.1.34;
}
host arcade {
hardware ethernet 00:23:ae:6f:8e:a7;
fixed-address 10.8.1.35;
}
host inventory {
hardware ethernet 90:e6:ba:84:b6:e0;
fixed-address 10.8.1.38;
}
host camera {
hardware ethernet 52:54:00:1f:63:1b;
fixed-address 10.8.1.39;
}
# Cisco IP Phone
host SEPA40CC394DB0C {
hardware ethernet a4:0c:c3:94:db:0c;
next-server 10.8.1.2;
# managed by dfgg/drozdziak
#option cisco-ip-phone-tftp 10.8.0.190;
option cisco-ip-phone-tftp 10.8.1.2;
fixed-address 10.8.1.42;
}
# RIPE Atlas Probe
host ripeatlas {
hardware ethernet c0:25:e9:99:fb:e8;
fixed-address 10.8.1.43;
}
host chromecast {
hardware ethernet 6c:ad:f8:52:4c:a7;
fixed-address 10.8.1.47;
}
# craptrap VM
host winbox {
hardware ethernet 52:54:00:D9:DB:42;
fixed-address 10.8.1.48;
}
host staszkecoin {
hardware ethernet 02:42:24:75:eb:19;
fixed-address 10.8.1.49;
}
host blitzloop {
hardware ethernet 00:23:14:b0:ec:c8;
fixed-address 10.8.1.51;
}
host tronxy {
hardware ethernet 00:1f:16:1c:47:df;
fixed-address 10.8.1.52;
}
host tv1 {
hardware ethernet dc:a6:32:b1:68:d7;
fixed-address 10.8.1.53;
}
host tv2 {
hardware ethernet dc:a6:32:b1:68:83;
fixed-address 10.8.1.54;
}
# kodak
host akamanto {
hardware ethernet b8:27:eb:d7:b9:ae;
fixed-address 10.8.1.55;
}
# voron
host karasu-tengu {
hardware ethernet b8:27:eb:00:f8:f5;
fixed-address 10.8.1.56;
}
}
# Printer subnet (10.10.7.0/24) has ip-helper 10.8.1.2 set on hs-core01.
# Make DHCP happen.
subnet 10.10.7.0 netmask 255.255.255.0 {
option routers 10.10.7.1;
range 10.10.7.100 10.10.7.200;
authoritative;
allow bootp;
}
# Listen for relayed requests on the interface from core01
# (even though we're not serving anything there directly)
subnet 172.16.1.0 netmask 255.255.255.250 {
}
subnet 10.10.5.0 netmask 255.255.255.0 {
option routers 10.10.5.1;
range 10.10.5.100 10.10.5.200;
authoritative;
allow bootp;
filename "elilo.efi";
next-server 10.8.1.16;
# option pxelinux.configfile "elilo.conf"
}
# itanic ilo gnuj
subnet 10.10.1.0 netmask 255.255.255.0 {
option routers 10.10.1.1;
range 10.10.1.150 10.10.1.200;
authoritative;
next-server 10.8.1.16;
}
subnet 10.11.1.0 netmask 255.255.255.0 {
option routers 10.11.1.1;
option domain-name-servers 10.11.1.1;
range 10.11.1.100 10.11.1.200;
authoritative;
default-lease-time 600;
max-lease-time 600;
}

View File

@ -0,0 +1,136 @@
{ config, pkgs, lib, ... }:
let
keaReservationsPreformat = lib.attrsets.mapAttrsToList (name: val: {
hostname = val.hostname;
hw-address = name;
ip-address = val.ip;
});
in {
services.kea = {
dhcp4 = {
enable = true;
settings = {
interfaces-config = { interfaces = [ "lan" "bms" ]; };
lease-database = {
name = "/var/lib/kea/dhcp4.leases";
persist = true;
type = "memfile";
};
rebind-timer = 300;
renew-timer = 150;
valid-lifetime = 600;
# yanked from https://kea.readthedocs.io/en/latest/arm/dhcp4-srv.html#setting-fixed-fields-in-classification
# if i understand correctly, the logic is reversed to what isc-dhcp
# config did, but result should be the same
client-classes = [{
name = "ipxe_efi_x64";
test = "option[93].hex == 0x0009";
boot-file-name = "netboot.xyz.efi";
}];
subnet4 = [
{ # general members area lan
subnet = "10.8.0.0/16";
pools = [{ pool = "10.8.0.20 - 10.8.0.199"; }];
reservations-out-of-pool = false;
reservations-in-subnet = true;
authoritative = true;
next-server = "10.8.1.2";
option-data = [
{
name = "routers";
data = "10.8.1.2";
}
{
name = "domain-name-servers";
data = "10.8.1.2";
}
{
name = "boot-file-name";
data = "netboot.xyz.kpxe";
}
];
reservations = keaReservationsPreformat {
# cat old-dhcpd.conf | sed -e 's/;//g' | awk '
# $1 == "host" { hostname = $2; pp = "yes"; }
# $1 == "hardware" { hwaddr = $3; }
# $1 == "fixed-address" { ip = $2; }
# $1 == "}" && pp == "yes" {
# print "\"" hwaddr "\" = { ip = \"" ip "\"; hostname = \"" hostname "\"; };"
# pp = "no"
# }'
"00:0e:35:1d:a1:a4" = { ip = "10.8.1.18"; hostname = "laser"; };
# set here just for completeness sake; the printer for some
# reason doesn't accept dhcp offers from kea.
"00:25:36:de:27:56" = { ip = "10.8.1.20"; hostname = "oki"; };
"00:1b:a9:24:96:e2" = { ip = "10.8.1.21"; hostname = "brother"; };
"00:07:4d:4d:71:e4" = { ip = "10.8.1.22"; hostname = "zebra"; };
"00:30:C1:62:61:23" = { ip = "10.8.1.23"; hostname = "lj2100"; };
"5c:cf:7f:06:9a:3e" = { ip = "10.8.1.25"; hostname = "dht21"; };
"00:0A:35:00:01:22" = { ip = "10.8.1.26"; hostname = "ledpanel"; };
"b8:27:eb:ed:df:f9" = { ip = "10.8.1.17"; hostname = "printmaster"; };
"90:1b:0e:1d:23:09" = { ip = "10.8.1.29"; hostname = "bridgeport"; };
"02:20:f5:20:6a:2d" = { ip = "10.8.1.30"; hostname = "3printers1cups"; };
"fe:77:d6:83:26:b1" = { ip = "10.8.1.31"; hostname = "telelele"; };
"b8:27:eb:03:69:01" = { ip = "10.8.1.32"; hostname = "vending"; };
"b0:38:29:2e:5d:c9" = { ip = "10.8.1.33"; hostname = "transcend"; };
"b8:27:eb:37:9e:6e" = { ip = "10.8.1.34"; hostname = "welcomer"; };
"00:23:ae:6f:8e:a7" = { ip = "10.8.1.35"; hostname = "arcade"; };
"90:e6:ba:84:b6:e0" = { ip = "10.8.1.38"; hostname = "inventory"; };
"52:54:00:1f:63:1b" = { ip = "10.8.1.39"; hostname = "camera"; };
# RIPE Atlas Probe
"c0:25:e9:99:fb:e8" = { ip = "10.8.1.43"; hostname = "ripeatlas"; };
"6c:ad:f8:52:4c:a7" = { ip = "10.8.1.47"; hostname = "chromecast"; };
# craptrap VM
"52:54:00:D9:DB:42" = { ip = "10.8.1.48"; hostname = "winbox"; };
"02:42:24:75:eb:19" = { ip = "10.8.1.49"; hostname = "staszkecoin"; };
"00:23:14:b0:ec:c8" = { ip = "10.8.1.51"; hostname = "blitzloop"; };
"00:1f:16:1c:47:df" = { ip = "10.8.1.52"; hostname = "tronxy"; };
"dc:a6:32:b1:68:d7" = { ip = "10.8.1.53"; hostname = "tv1"; };
"dc:a6:32:b1:68:83" = { ip = "10.8.1.54"; hostname = "tv2"; };
# kodak
"b8:27:eb:d7:b9:ae" = { ip = "10.8.1.55"; hostname = "akamanto"; };
# voron
"b8:27:eb:00:f8:f5" = { ip = "10.8.1.56"; hostname = "karasu-tengu"; };
};
}
{ # bms
subnet = "10.11.1.0/24";
pools = [{ pool = "10.11.1.100 - 10.11.1.200"; }];
reservations-out-of-pool = false;
reservations-in-subnet = true;
authoritative = true;
option-data = [
{
name = "routers";
data = "10.11.1.1";
}
{
name = "domain-name-servers";
data = "10.11.1.1";
}
];
}
];
};
};
};
users.users.kea = {
group = "kea";
isSystemUser = true;
};
users.groups.kea = {};
systemd.services.kea-dhcp4-server.serviceConfig = {
UMask = lib.mkForce "0033";
DynamicUser = lib.mkForce false;
};
}