[systemd-devel] systemd/hostnamed: setting the hostname and using it in the DHCP Discover

Lennart Poettering lennart at poettering.net
Mon Jul 31 14:24:27 UTC 2017


On Fr, 28.07.17 12:08, Andrey Yurovsky (yurovsky at gmail.com) wrote:

> I have an embedded target where the hostname is expected to be a
> string derived in part from the MAC address of an Ethernet interface.
> I've been looking at how to properly set the system's hostname and
> also have systemd-networkd use it in the DHCP request it sends out,
> however there seems to be an order of operations issue.
> 
> 1. in systemd/core/main.c the /etc/hostname contents are unconditionally read
> 2. I can add a service that uses the special network-pre.target to
> override /etc/hostname with my generated string and I see that while
> the initial string is pickedup by systemd, the new hostname will in
> fact be used
> 3. I then have a .network file specifying DHCP on that Ethernet interface
> 
> But then on initial boot I see that the DHCP Discover coming out has
> option 12 set to the original hostname that systemd picked up in
> main.c, even though the network-pre.target caused my unit to run. I
> can then reboot the system and this time main.c picks up the "new"
> hostname and option 12 is indeed set to this.
> 
> One workaround I found was to have my unit write the Hostname= option
> to the .network file but that seems like the wrong approach.
> 
> Is there a correct way to replace or otherwise set the hostname and
> have systemd use it from the beginning and ensure that the DHCP client
> specifies it in option 12?

Hmm, I am not sure I follow. Do you want the hostname to be "sticky"?
i.e. if you boot up once, and your special hostname is not initialized
yet, you initialize from whatever the MAC address is, and then store
it to /etc/hostname, and from that point on and for all future boots
it's supposed to stay fixed? Or do you want it to be fully
dynamic: as soon as an ethernet device shows up, set the hostname,
and when no device has shown up the hostname should remain
uninitialized, and on subsequent boot everything starts from fresh,
with no previous data?

Under the assumption you want the latter: just drop /etc/hostname, so
that no static hostname is managed by systemd/hostnamed. In this case
the system will boot up with the fallback hostname (which is
"localhost" unless your distro overrides that at compile time). Then,
add a udev rule that is run when an interface shows up, and that
changes the hostname as necessary, maybe by invoking the
/usr/bin/hostname binary.

The DHCP client in networkd will query the hostname the instant it
starts setting up the DHCP session. It will use whatever is set at
that point in time. Hence, if you set the hostname from the udev rule
things should be properly race-free as networkd will only take
possession of any interface after the udev rule ran, and hence will
necessarily initialize its DHCP client at a point in time the hostname
is set to what you want it to be set to.

Lennart

-- 
Lennart Poettering, Red Hat


More information about the systemd-devel mailing list