Kea DHCP Daemon

I’ve used Internet Software Consortium’s dhcpd for a while.

When I was setting up my new server I found out that dhcpd was past end-of-life. ISC wanted me to use kea instead.

I use DNSMasq as a DNS aggregator on my LAN, because ISC’s bind had huge latency and was generally ugly to setup. I could use DNSMasq as both DHCP server and DNS aggregator. That has some advantages, as random machines that join the network via DHCP get put into (local) DNS, if you configure correctly.

I’m a little leery of combining disparate functions, so I’m going to set up kea-dhcp4 on my new Qotom server.

I used the Arch Linux Wiki kea entry as my guide.

diagram of network for this post

For purposes of this post, that’s my network. I’m trying to get the Qotom server to do DHCP for all things requesting an IP address to its left, which is the OpenWrt WiFi access point, and all of the access point’s clients. Currently, that’s just my Arch Linux laptop.

Ultimately, the Qotom server will take the place of the Dell R530 server, but for now, the Qotom server is (in turn) a DHCP client of the R530.

Config file

One of the things that initially turned me off about kea is that the ISC website touts the use of MySQL or Postgres database back ends. That sort of thing is very “enterprise”, and always seems to cause trouble. Maybe “enterprises” can afford someone to monitor MySQL or Postgres instances, but I just can’t.

You don’t have to use MySQL or Postgres back ends, you can configure kea-dhcp4 to use a CSV file for leases and such. The config file wasn’t that hard to get right.

One of the nicer things about kea is that it can read and check its config file very easily with kea-dhcp4 -t /etc/kea/kea-dhcp4.conf. A non-root user can run the check, but root has to edit the config file.

I used the automatic checking diligently.

I think I’m going to also try to renumber my network from 10.0.0.0/8 to 174.16.0.0/20 while I’m doing this.

First Client

I thought I would use my WRT3200ACM WiFi router as my first client. I could connect to a bridged WiFi with my phone or laptop and kea would provide an IPv4 address.

First Obstacle

Welp, my first client didn’t work.

tcpdump -i enp4s0 on Qotom showed only BOOTP/DHCP Requests, no replies from kea-dhcp4.

22:14:02.339700 IP 0.0.0.0.bootpc > broadcasthost.bootps: BOOTP/DHCP, Request from 6c:cd:d6:c0:dc:7d (oui Unknown), length 300

I looked through the config file and noticed I had set “udp” instead of “raw” socket for kea-dhcp4 to listen on.

Setting it to “raw” solved that problem.

tcpdump -i enp4s0 on Qotom showed BOOTP/DHCP Request and Reply packets.

Second Obstacle

Still didn’t work. The WiFi “dongle” on my laptop could authenticate itself to the WRT3200ACM wireless, but never picked up an IPv4 address.

Ran tcpdump on the Qotom interface, enp4s0, journalctl -f -u kea-dhcp4 on Qotom journalctl -f -u dhcpcd on laptop. Ran tcpdump on the laptop’s WiFi dongle interface.

The journalctl’s were superfluous, but did show kea-dhcp4 and dhcpcd were both working. The laptop sent DHCP Request packets at regular intervals.

tcpdump on Qotom showed DHCP Request and DHCP Reply packets. tcpdump on laptop only showed DHCP Request packets. WTF?

Took my laptop over to the Qotom in the server I mean furnace room and physically plugged the laptop’s ethernet port into one of the WRT3200ACM’s ethernet ports, with tcpdump watching packets on the laptop’s ethernet port. No DHCP Reply packets.

I could not get a shell on the WRT3200ACM, either. I had previously configured OpenWrt on the WRT3200ACM to be available on the bridged LAN like this (/etc/config/network):

config interface 'lan'
        option device 'br-lan'
        option proto 'static'
        option ipaddr '10.0.0.145'
        option netmask '255.255.255.0'
        option ip6assign '60'

After reworking the cable so that the WRT3200ACM was plugged in to my R530, I changed the config to this, so as to be able to get to an OpenWrt shell from the new server:

                            
config interface 'lan'      
        option device 'br-lan'
        option proto 'dhcp'   

I edited /etc/kea/kea-dhcp4.conf to give OpenWrt’s LAN MAC address a stable IPv4 address, took the WRT3200ACM back to the furnace room, plugged it into the Qotom server. Whatta ya know, my laptop, when authenticated to the WRT3200ACM’s wireless, got DHCP Reply packets. This is a completely inobvious consequence of getting OpenWrt’s LAN interface wrong. Why should it not bridge DHCP Reply packets if it doesn’t have an appropriate network address? I still don’t understand this one.

Third Obstacle

I noticed that my laptop, when connected to the WiFi bridge of the Second Obstacle, sometimes took quite a long time, one or two minutes sometimes, to acquire an IPv4 address.

Running tcpdump on the Qotom server hardware (which has kea-dhcp4 running), I see this:

21:26:07.539100 IP 0.0.0.0.68 > 255.255.255.255.67: BOOTP/DHCP, Request from e4:a4:71:30:21:86, length 300
21:26:07.542178 IP 172.24.0.1.67 > 172.24.0.7.68: BOOTP/DHCP, Reply, length 334
21:26:11.056857 IP 0.0.0.0.68 > 255.255.255.255.67: BOOTP/DHCP, Request from e4:a4:71:30:21:86, length 300
21:26:11.059631 IP 172.24.0.1.67 > 172.24.0.7.68: BOOTP/DHCP, Reply, length 334
21:26:12.557774 IP 0.0.0.0.68 > 255.255.255.255.67: BOOTP/DHCP, Request from e4:a4:71:30:21:86, length 300
21:26:12.560841 IP 172.24.0.1.67 > 172.24.0.7.68: BOOTP/DHCP, Reply, length 334
21:26:16.552123 IP 0.0.0.0.68 > 255.255.255.255.67: BOOTP/DHCP, Request from e4:a4:71:30:21:86, length 300
21:26:16.554829 IP 172.24.0.1.67 > 172.24.0.7.68: BOOTP/DHCP, Reply, length 334
21:26:24.551266 IP 0.0.0.0.68 > 255.255.255.255.67: BOOTP/DHCP, Request from e4:a4:71:30:21:86, length 300
21:26:24.553291 IP 172.24.0.1.67 > 172.24.0.7.68: BOOTP/DHCP, Reply, length 334
21:26:41.275985 IP 0.0.0.0.68 > 255.255.255.255.67: BOOTP/DHCP, Request from e4:a4:71:30:21:86, length 300
21:26:41.278775 IP 172.24.0.1.67 > 172.24.0.7.68: BOOTP/DHCP, Reply, length 334
21:27:13.818213 IP 0.0.0.0.68 > 255.255.255.255.67: BOOTP/DHCP, Request from e4:a4:71:30:21:86, length 300
21:27:13.821319 IP 172.24.0.1.67 > 172.24.0.7.68: BOOTP/DHCP, Reply, length 334
21:28:17.420034 IP 0.0.0.0.68 > 255.255.255.255.67: BOOTP/DHCP, Request from e4:a4:71:30:21:86, length 300
21:28:17.422251 IP 172.24.0.1.67 > 172.24.0.7.68: BOOTP/DHCP, Reply, length 334
21:28:17.426406 IP 0.0.0.0.68 > 255.255.255.255.67: BOOTP/DHCP, Request from e4:a4:71:30:21:86, length 300
21:28:17.428572 IP 172.24.0.1.67 > 172.24.0.7.68: BOOTP/DHCP, Reply, length 334
21:28:17.431588 ARP, Request who-has 172.24.0.7 tell 0.0.0.0, length 46
21:28:18.555427 ARP, Request who-has 172.24.0.7 tell 0.0.0.0, length 46
21:28:20.083366 ARP, Request who-has 172.24.0.7 tell 0.0.0.0, length 46
21:28:22.088791 ARP, Request who-has 172.24.0.7 tell 172.24.0.7, length 46
21:28:23.088943 ARP, Request who-has 172.24.0.1 tell 172.24.0.7, length 46
21:28:23.088963 ARP, Reply 172.24.0.1 is-at 20:7c:14:f3:83:02, length 28

That’s nine DHCP “discover” and “offer” pairs.

But only the last two reply packets get through to dhcpcd on my Linux laptop. This may mean that I didn’t really solve the Second Obstacle.

I consulted the wise ones that answer questions in the OpenWrt forum. I found out that I had not really overcome the Second Obstacle at all.

Upgrade OpenWrt

  • I had installed OpenWrt 23.05.0, part of the advice I got was to upgrade to 23.05.3
    • I re-experienced the usual 3 minutes of uncertainty as sysupgrade -n -v openwrt-23.05.3-mvebu-cortexa9-linksys_wrt3200acm-squashfs-sysupgrade.bin took effect
    • Had to plug the CAT-5 cable from the Qotom server into the “Internet” ethernet port of the WRT3200ACM
    • Then, I had to use another CAT-5 cable to connect my laptop to the WRT3200ACM in order to ssh to the OpenWrt command line. OpenWrt 23.05.3 does not enable the radios initially.
    • Apparently there’s a bug in OpenWrt that means you have to turn off the WRT3200ACM’s third radio.
      1. opkg remove kmod-mwifiex-sdio
      2. wifi config > /etc/config/wireless (WTF does this even do?)
      3. reboot
    • Had to enable the radios on the newly-installed OpenWrt
      1. uci set wireless.radio0.country='US'
      2. uci set wireless.radio1.country='US'
      3. uci set wireless.radio1.disabled='0'
      4. uci set wireless.radio0.disabled='0'
      5. uci commit wireless
      6. wifi reload
    • Added encryption to the WiFi. Made a piece of /etc/config/wireless look like this:
config wifi-iface 'default_radio0'
        option device 'radio0'
        option network 'lan'
        option mode 'ap'
        option ssid 'bongrips4jesus42069'
        option encryption 'psk2'
        option key 'paswordpassword'

That seemed to allow my laptop to pick up an IPv4 address in about 22 seconds, which is better than 90 seconds or 5 minutes.

Now to make the whole “lan” interface of OpenWrt, which is the WiFi radios and 4 RJ-45 ethernet ports on the back a big ol’ “bridge” again.

I didn’t do the “dumb APD” as I did before. On advice of one of the OpenWrt sages, I changed a piece of /etc/config/dhcp to this:

config dhcp 'lan'
        option interface 'lan'
        option start '100'
        option limit '150'
        option leasetime '12h'
        option dhcpv4 'server'
        option ignore '1'

The OpenWrt forum sage advised against explicitly turning off dnsmasq, dhcpd, odhcpd and firewall, but rather ignoring the interface.

This seems to work. kea-dhcpd4 running on the Qotom server is supplying my laptop and the WRT3200ACM IPv4 addresses in the 172.16.0.0/20 range, and also sets DNS server to 172.24.0.1. IPv4 addresses don’t take minutes to acquire.

This was an adventure, but I’m going to call transitioning to kea a qualified success. I’m going to keep my eye on address acquisition time, and see how easy kea is to administer and run.