Preface
I'm building a virtualization environment with Ubuntu 14.04 and LXC. I don't want to write my own template since the upgrade from 12.04 to 14.04 has shown that backwards compatibility is not guaranteed.
Therefore I'm deploying my virtual machines via lxc-create, using the default Ubuntu template. The DNS for the servers is provided by Amazon Route 53, so no local DNS server is needed.
I also use Puppet to configure my servers, so I want to keep the manual effort on the deployment minimal.
Now, the default Ubuntu template assigns IP addresses via DHCP. Therefore, I need a local DHCP server to assign IP addresses to the nodes, so I can SSH into them and get Puppet running. Since Puppet requires a proper DNS setup, assigning temporary IP addresses is not an option, the client needs to get the right hostname and IP address from the start.
Question
What DHCP server do I use and how do I get it to assign the IP address based only on the host-name DHCP option by performing a DNS lookup on that very host name?
What I've tried
I tried to make it work using the ISC DHCP server, however, the manual clearly states:
Please be aware that only the dhcp-client-identifier option and the hardware address can be used to match a host declaration, or the host-identifier option parameter for DHCPv6 servers. For example, it is not possible to match a host declaration to a host-name option. This is because the host-name option cannot be guaranteed to be unique for any given client, whereas both the hardware address and dhcp-client-identifier option are at least theoretically guaranteed to be unique to a given client.
I also tried to create a class that matches the hostname like this:
class "my-client-name" {
match if option host-name = "my-client-name";
fixed-address my-client-name.my-domain.com;
}
Unfortunately the fixed-address option is not allowed in class statements. I can replace it with a 1-size pool, which works as expected:
subnet 10.103.0.0 netmask 255.255.0.0 {
option routers 10.103.1.1;
class "my-client-name" {
match if option host-name = "my-client-name";
}
pool {
allow members of "my-client-name";
range 10.103.1.2 10.103.1.2;
}
}
However, this would require me to administer the IP addresses in two places (Amazon Route53 and the DHCP server), which I would prefer not to do.
About security
Since this is only used in the bootstrapping phase on an internal network and is then replaced by a static network configuration by Puppet, this shouldn't be an issue from a security standpoint. I am, however, aware that the virtual machine bootstraps with "ubuntu:ubuntu" credentials, which I intend to fix once this is running.