New IP address whereas DHCP lease time not out

dhcpsystemdsystemd-networkd

My embedded system uses systemd and gets its IP address via DHCP. The DHCP server uses lease time to give the same IP unique address to every computer on the network if lease time is respected.

The network configuration of my embedded system is as follow :

/etc/systemd/network/dhcp.network

[Match]
Name=eth*

[Network]
DHCP=yes

The problem is that at every boot, I get a new IP address on my system. Is there some configuration I'm missing ?

some more info :

$ cat /proc/version
Linux version 4.16.0 (aurelien@l2.lf) (gcc version 7.3.0 (Buildroot 2018.05-g0164235-dirty)) #18 SMP PREEMPT Tue Jul 17 14:28:37 CEST 2018  

[EDIT] Add DHCP Discover paquet

Frame 13299: 327 bytes on wire (2616 bits), 327 bytes captured (2616 bits) on interface 0  
    Interface id: 0 (\\.\pipe\Shamrock_Wireshark_TAP__30815)  
    Encapsulation type: Ethernet (1)  
    Arrival Time: Jul 16, 2018 10:39:49.166800000 Paris, Madrid (heure d??t?)  
    [Time shift for this packet: 0.000000000 seconds]  
    Epoch Time: 1531730389.166800000 seconds  
    [Time delta from previous captured frame: 20.554641000 seconds]  
    [Time delta from previous displayed frame: 43.658782000 seconds]  
    [Time since reference or first frame: 43.770160000 seconds]  
    Frame Number: 13299  
    Frame Length: 327 bytes (2616 bits)  
    Capture Length: 327 bytes (2616 bits)  
    [Frame is marked: False]  
    [Frame is ignored: False]  
    [Protocols in frame: eth:ethertype:ip:udp:bootp]  
    [Coloring Rule Name: UDP]  
    [Coloring Rule String: udp]  
Ethernet II, Src: AlstomGr_20:00:6f (80:b3:2a:20:00:6f), Dst: Broadcast (ff:ff:ff:ff:ff:ff)  
    Destination: Broadcast (ff:ff:ff:ff:ff:ff)  
        Address: Broadcast (ff:ff:ff:ff:ff:ff)  
        .... ..1. .... .... .... .... = LG bit: Locally administered address (this is NOT the factory default)  
        .... ...1 .... .... .... .... = IG bit: Group address (multicast/broadcast)  
    Source: AlstomGr_20:00:6f (80:b3:2a:20:00:6f)  
        Address: AlstomGr_20:00:6f (80:b3:2a:20:00:6f)  
        .... ..0. .... .... .... .... = LG bit: Globally unique address (factory default)  
        .... ...0 .... .... .... .... = IG bit: Individual address (unicast)  
    Type: IPv4 (0x0800)
Internet Protocol Version 4, Src: 0.0.0.0, Dst: 255.255.255.255  
    0100 .... = Version: 4  
    .... 0101 = Header Length: 20 bytes  
    Differentiated Services Field: 0xc0 (DSCP: CS6, ECN: Not-ECT)  
        1100 00.. = Differentiated Services Codepoint: Class Selector 6 (48)  
        .... ..00 = Explicit Congestion Notification: Not ECN-Capable Transport (0)  
    Total Length: 313  
    Identification: 0x0000 (0)  
    Flags: 0x00  
        0... .... = Reserved bit: Not set  
        .0.. .... = Don't fragment: Not set  
        ..0. .... = More fragments: Not set  
    Fragment offset: 0  
    Time to live: 64  
    Protocol: UDP (17)  
    Header checksum: 0x78f5 [validation disabled]  
        [Good: False]  
        [Bad: False]  
    Source: 0.0.0.0  
    Destination: 255.255.255.255  
    [Source GeoIP: Unknown]  
    [Destination GeoIP: Unknown]  
User Datagram Protocol, Src Port: 68 (68), Dst Port: 67 (67)  
    Source Port: 68  
    Destination Port: 67  
    Length: 293  
    Checksum: 0xca77 [validation disabled]  
        [Good Checksum: False]  
        [Bad Checksum: False]  
    [Stream index: 0]   
Bootstrap Protocol (Discover)  
    Message type: Boot Request (1)  
    Hardware type: Ethernet (0x01)  
    Hardware address length: 6  
    Hops: 0  
    Transaction ID: 0x240b826b  
    Seconds elapsed: 1  
    Bootp flags: 0x0000 (Unicast)  
        0... .... .... .... = Broadcast flag: Unicast  
        .000 0000 0000 0000 = Reserved flags: 0x0000  
    Client IP address: 0.0.0.0  
    Your (client) IP address: 0.0.0.0  
    Next server IP address: 0.0.0.0  
    Relay agent IP address: 0.0.0.0  
    Client MAC address: AlstomGr_20:00:6f (80:b3:2a:20:00:6f)  
    Client hardware address padding: 00000000000000000000  
    Server host name not given  
    Boot file name not given  
    Magic cookie: DHCP  
    Option: (53) DHCP Message Type (Discover)  
        Length: 1  
        DHCP: Discover (1)  
    Option: (61) Client identifier  
        Length: 19  
        IAID: cd4578d2  
        DUID Type: assigned by vendor based on Enterprise number (2)  
        Enterprise-number: Tom Gundersen (systemd) (43793)  
        Identifier: 871468cb35ae1ddc  
    Option: (55) Parameter Request List  
        Length: 8  
        Parameter Request List Item: (1) Subnet Mask  
        Parameter Request List Item: (3) Router  
        Parameter Request List Item: (12) Host Name  
        Parameter Request List Item: (15) Domain Name  
        Parameter Request List Item: (6) Domain Name Server  
        Parameter Request List Item: (33) Static Route  
        Parameter Request List Item: (121) Classless Static Route  
        Parameter Request List Item: (42) Network Time Protocol Servers  
    Option: (57) Maximum DHCP Message Size  
        Length: 2  
        Maximum DHCP Message Size: 576  
    Option: (12) Host Name  
        Length: 4  
        Host Name: RPH4  
    Option: (255) End  
        Option End: 255

Best Answer

The DHCP Discover packet includes a RFC 4361-style client identifier (option 61, also known as DUID) with systemd's Enterprise number (43793). This is because your /etc/systemd/network/dhcp.network file does not include the ClientIdentifier nor DUIDType settings; the defaults are ClientIdentifier=duid and DUIDType=vendor.

The DUIDType=vendor default setting causes systemd-networkd to generate the DUID by using the above-mentioned Enterprise number and hashed contents of /etc/machine-id. The machine-id should be generated at first boot of the system and then stay the same for the lifetime of the system (or the lifetime of the OS installation at least).

If your embedded system is not configured to store this machine-id persistently, it will be generated randomly at every boot... which would then cause the behavior you're seeing.

If you don't need your system to use IPv6-compliant DUID identifiers, the easiest fix would be to specify that this system should use its MAC address as DHCP client identifier. This can be achieved by adding this to your dhcp.network file:

[DHCP]
ClientIdentifier=mac

If you are also using DHCPv6, and/or you need to identify your DHCP clients using an identifier that is specific to the system and not its particular NIC, then you should read the documentation for systemd's network configuration files and find a combination of settings that suits your needs.

Related Question