Valid HTML 4.01 Transitional
Prev: EFI Booting a Virtual Machine with BTRFS Root
(Index)
Jim Carter's Bugfixes

DHCP IPv6 Gets Pool Address, not Assigned IP

James F. Carter
2023-02-18
Symptom:

Whereas most people use RFC 4862 autoconfiguration to get an IPv6 address on their hosts, CouchNet has a fixed address (IPv4+6) assigned to each host, and the Router Advertisements tell the client to use DHCPv6 to discover that address. For guests, the DHCP server (Kea) also has a pool of dynamically assigned addresses. As belt and suspender overkill, hosts have their fixed address configured locally as a fallback if DHCPv6 is not working. A few hosts can't do fallback. Some hosts have wild-side addresses: the main router, and my laptop when roaming.

Indeed, DHCPv6 is messed up for some but not all hosts, and they get a pool address. They also get their fallback address if capable. I tried for several years to get this working. When my hoem automation server could not communicate on IPv6, I got aggressive and finally found out what was happening and how to fix it.

What's happening:

In DHCP the DUID is the DHCP User Identifier. In DHCPv4 the host's MAC address is normally (but not always) used as the DUID, although modern standards revisions allow a DHCPv6 DUID to also be sent. On my DHCP server (both DHCPv4+6) the MAC is configured with each static lease, not a DUID, and Kea is able in DHCPv4 to use the client's MAC to find its static IPv4 address. Similarly, when wicked is the client, Kea can use the information provided, including the MAC, in solicitation packets from some but not all hosts to find their assigned IPv6 addresses.

If a host for DHCPv6 provides a DUID that has the wrong MAC address, or if it uses a DUID type that doesn't include the MAC, Kea has no idea that the host has a fixed IP, and assigns it something from the pool: the behavior complained about.

Remember that the host normally has a different MAC on each network interface, but the DUID is supposed to be the same for all interfaces (except in special cases). In other words, you are supposed to pick one MAC as the official one, and to use that in the static lease configuration for Kea, as well as in the DUID.

How to fix:

For Wicked, it is usually sufficient to just remove /var/lib/wicked/duid.xml , restart Wicked, and it will generate a new one, type 3 with a timestamp and the MAC of the interface that DHCP packets are going to be sent from at that time. This DUID will persist until removed and it will be used for all interfaces on the node.

My laptop could use Wi-Fi (802.11) or wired Ethernet (802.3) (not both at the same time), and it also has a bridge containing the virtual NIC of a virtual machine. The bridge has the official IPv4+6 and MAC addresses of the laptop, it is configured as a rounter (for the guest), and the default route goes out via Wi-Fi or Ethernet, depending on which one can contact the DHCP server. It also uses NetworkManager, which is a whole other can of worms.

NetworkManager has a separate DUID for each persistent connection. These are stored in /var/lib/NetworkManager/dhclient6-$UUID-$NIC.lease, e.g. dhclient6-f38c193b-91f8-41d5-98ed-a695fac4fe93-en0.lease. (Don't mess with the DHCPv4 and internal files in this directory.) The UUID is found in /etc/NetworkManager/system-connections/$CONN (the connection's configuration file), linking the DUID and the connection. The lease file (IPv6 only) contains just one line:
default-duid "\000\003\000\001RT\000\011\310\261";
(showing my laptop's DUID as an example; I doubt the GRU or FSB are going to do an exploit against me on my home net.) Formerly it had a type 4 DUID with a random-looking UUID, same for all the connections, which I could have kept, except that I put together a checking script that compares the official MAC with the one that isn't in the DUID, and complains. I could just give a pass to type 2 and type 4 DUIDs, or I could create a type 1 or type 3 DUID that ends with the official MAC address, and being ornery I picked the latter solution.


Prev: EFI Booting a Virtual Machine with BTRFS Root
(Index)