Use dnsmasq to provide DNS & DHCP services

Provide DNS & DHCP with dnsmasq

Many tech enthusiasts find the ability to control their host name resolution important. Setting up servers and services usually requires some form of fixed address, and sometimes also requires special forms of resolution such as defining Kerberos or LDAP servers, mail servers, etc. All of this can be achieved with dnsmasq.

dnsmasq is a lightweight and simple program which enables issuing DHCP addresses on your network and registering the hostname & IP address in DNS. This configuration also allows external resolution, so your whole network will be able to speak to itself and find external sites too.

This article covers installing and configuring dnsmasq on either a virtual machine or small physical machine like a Raspberry Pi so it can provide these services in your home network or lab. If you have an existing setup and just need to adjust the settings for your local workstation, read the previous article which covers configuring the dnsmasq plugin in NetworkManager.

Install dnsmasq

First, install the dnsmasq package:

sudo dnf install dnsmasq

Next, enable and start the dnsmasq service:

sudo systemctl enable --now dnsmasq

Configure dnsmasq

First, make a backup copy of the dnsmasq.conf file:

sudo cp /etc/dnsmasq.conf /etc/dnsmasq.conf.orig

Next, edit the file and make changes to the following to reflect your network. In this example, mydomain.org is the domain name, 192.168.1.10 is the IP address of the dnsmasq server and 192.168.1.1 is the default gateway.

sudo vi /etc/dnsmasq.conf

Insert the following contents:

domain-needed
bogus-priv
no-resolv
server=8.8.8.8
server=8.8.4.4
local=/mydomain.org/
listen-address=::1,127.0.0.1,192.168.1.10
expand-hosts
domain=mydomain.org
dhcp-range=192.168.1.100,192.168.1.200,24h
dhcp-option=option:router,192.168.1.1
dhcp-authoritative
dhcp-leasefile=/var/lib/dnsmasq/dnsmasq.leases

Test the config to check for typos and syntax errors:

$ sudo dnsmasq --test
dnsmasq: syntax check OK.

Now edit the hosts file, which can contain both statically- and dynamically-allocated hosts. Static addresses should lie outside the DHCP range you specified earlier. Hosts using DHCP but which need a fixed address should be entered here with an address within the DHCP range.

sudo vi /etc/hosts

The first two lines should be there already. Add the remaining lines to configure the router, the dnsmasq server, and two additional servers.

127.0.0.1   localhost localhost.localdomain
::1         localhost localhost.localdomain
192.168.1.1    router
192.168.1.10   dnsmasq
192.168.1.20   server1
192.168.1.30   server2

Restart the dnsmasq service:

sudo systemctl restart dnsmasq

Next add the services to the firewall to allow the clients to connect:

sudo firewall-cmd --add-service={dns,dhcp}
sudo firewall-cmd --runtime-to-permanent

Test name resolution

First, install bind-utils to get the nslookup and dig packages. These allow you to perform both forward and reverse lookups. You could use ping if you’d rather not install extra packages. but these tools are worth installing for the additional troubleshooting functionality they can provide.

sudo dnf install bind-utils

Now test the resolution. First, test the forward (hostname to IP address) resolution:

$ nslookup server1
Server:       127.0.0.1
Address:      127.0.0.1#53
Name:         server1.mydomain.org
Address:      192.168.1.20

Next, test the reverse (IP address to hostname) resolution:

$ nslookup 192.168.1.20
20.1.168.192.in-addr.arpa    name = server1.mydomain.org.

Finally, test resolving hostnames outside of your network:

$ nslookup fedoramagazine.org
Server:       127.0.0.1
Address:      127.0.0.1#53
Non-authoritative answer:
Name:    fedoramagazine.org
Address: 35.196.109.67

Test DHCP leases

To test DHCP leases, you need to boot a machine which uses DHCP to obtain an IP address. Any Fedora variant will do that by default. Once you have booted the client machine, check that it has an address and that it corresponds to the lease file for dnsmasq.

From the machine running dnsmasq:

$ sudo cat /var/lib/dnsmasq/dnsmasq.leases
1598023942 52:54:00:8e:d5:db 192.168.1.100 server3 01:52:54:00:8e:d5:db
1598019169 52:54:00:9c:5a:bb 192.168.1.101 server4 01:52:54:00:9c:5a:bb

Extending functionality

You can assign hosts a fixed IP address via DHCP by adding it to your hosts file with the address you want (within your DHCP range). Do this by adding into the dnsmasq.conf file the following line, which assigns the IP listed to any host that has that name:

dhcp-host=myhost

Alternatively, you can specify a MAC address which should always be given a fixed IP address:

dhcp-host=11:22:33:44:55:66,192.168.1.123

You can specify a PXE boot server if you need to automate machine builds

tftp-root=/tftpboot
dhcp-boot=/tftpboot/pxelinux.0,boothost,192.168.1.240

This should point to the actual URL of your TFTP server.

If you need to specify SRV or TXT records, for example for LDAP, Kerberos or similar, you can add these:

srv-host=_ldap._tcp.mydomain.org,ldap-server.mydomain.org,389
srv-host=_kerberos._udp.mydomain.org,krb-server.mydomain.org,88
srv-host=_kerberos._tcp.mydomain.org,krb-server.mydomain.org,88
srv-host=_kerberos-master._udp.mydomain.org,krb-server.mydomain.org,88
srv-host=_kerberos-adm._tcp.mydomain.org,krb-server.mydomain.org,749
srv-host=_kpasswd._udp.mydomain.org,krb-server.mydomain.org,464
txt-record=_kerberos.mydomain.org,KRB-SERVER.MYDOMAIN.ORG

There are many other options in dnsmasq. The comments in the original config file describe most of them. For full details, read the man page, either locally or online.

FAQs and Guides For System Administrators Using Software

16 Comments

  1. Joao Rodrigues

    Don’t forget to open ports in the firewall
    sudo firewall-cmd –add-service dhcp –add-service dns
    sudo firewall-cmd –runtime-to-permanent

    There are other public resolvers besides Google. A few examples include:
    CloudFlare:
    1.1.1.1
    1.0.0.1
    2606:4700:4700::1111
    2606:4700:4700::1001

    Quad9:
    9.9.9.9
    149.112.112.112
    2620:fe::11
    2620:fe::fe:11

    OpenDNS
    208.67.222.222
    208.67.220.220
    2620:119:35::35
    2620:119:53::53

  2. Pablo

    Hey Andy, thanks for the post! May I raise a couple questions:

    where are you making the machine should resolve names on itself? You didn’t mention anything about /etc/resolv.conf โ€“ I am a bit old school and I really feel I don’t know the resolver anymore xD
    you are enumerating some hosts in /etc/hosts but you didn’t mention how this gets into dnsmasq.

    While I was typing I re-read and figured out the linked article about the NetworkManager plugin gives some of the required background. But it is actually about NetworkManager and I feel that leaves us target readers with a bit of lack of context.

    • Hi Pablo, glad you found this useful.

      By default dnsmasq reads /etc/hosts for any configuration, so there’s no need to specifically add it in. This is one of the reasons I like to use it as it works seamlessly with a file people are usually familiar and comfortable with.

      Regarding resolution of itself, you’re correct and I didn’t mention that. As a DNS server the machine should have a static IP address, and on mine the resolv.conf file simply points to localhost:
      search mydomain.org
      nameserver 127.0.0.1

  3. Jean Forgeron

    I’d like to see a similar article focused around systemd services networkd and resolved.

    • Good news! I was talking to one of the systemd developers earlier today about writing an article on resolved. That’s one of the changes coming in Fedora 33.

  4. Bruno

    Nice article.
    Be sure to configure your Internet BOX to not use the same DHCP range as your dnsmasq config.
    You might have some machine configured by default to use Internet BOX (routeur) while some other are configured to use the machine you setup with dnsmasq. In this case there is a risk that the BOX DHCP service gives the same address as your dnsmasq DHCP service.
    Or does dnsmasq respond to DHCPDISCOVER broadcast ??
    Bruno

  5. Brian

    So I just need to turn off DCHP on my router and clients on my network will find this DHCP server automatically?

    Asking as my router does not do DNS, so this could fix that.

    • Hi Brian

      If you configure this on a machine with a network address on the same network as your router then it should offer DNS and DHCP for the network, so you should be able to turn off DHCP on your router and have this take its place.

    • I have yet to meet a router that doesn’t do DNS – but regardless, if you already have a proper Linux box that you can upgrade freely, you’re better off running your own full function Linux router with DHCP, DNS and arguably firewall etc

      • Vernon Van Steenkist

        Since Fedora and most other Linux Distributions, and printers and even Windows 10 support Apple’s Bonjour out of the box, the need for running a local DNS has become greatly diminished. For example, if you have a Raspberry Pi on your network, you can access it simply by typing

        ssh pi@raspberrypi.local

        assuming that you did not change the Raspberry Pi’s default host-name and username.

        Note that

        .local

        is the automatic Bonjour domain. So, machine’s on your network automagically gets assigned a fully qualified domain name of `hostname.local’

    • Brian

      Nice, thanks. Will give it a go.

  6. Christian von Behren

    cant get this fixed (worked fine in fedora32 though)

    dnsmasq[20478]: failed to create listening socket for port 53: Address already in use.

    Is there any new service compromosing dnsmasq beneath network-monitor?

    • Hi Christian

      It’s possibly systemd-resolved that’s bound to port 53. Try sudo ss -lp “sport = :domain” and see what the output is, then stop the service and try dnsmasq again. If it is the systemd-resolved service you could disable it, or you could change dnsmasq to listen on a different port.

      • Christian von Behren

        This is driving me nuts…

        Andy, You are right, NetworkManager seems to open a separate dnsmasq on 53.
        systemd-resolved gets in the way too…
        (https://fedoraproject.org/wiki/Changes/systemd-resolved#Split_DNS)
        Furthermore: Connected to an VPN, the only nameserver set in /etc/resolv.conf is 127.0.0.53 (which is not configured by /etc/dnsmasq.conf) though a different DNS Server is configured within vpn ipv4 settings in NetworkMonitor settings.
        Even when I set the company’s local DNS in /etc/resolve.conf, nslookup works fine and private vhost based wildcard subdomains get propperly resolved, I am unable to ping them ๐Ÿ™
        (looks like https://bugzilla.redhat.com/show_bug.cgi?id=504951)

        I am practically unable to work with this setup unless I setup every single project in /etc/hosts manually.

  7. Is commenting still permitted?

Comments are Closed

The opinions expressed on this website are those of each author, not of the author's employer or of Red Hat. Fedora Magazine aspires to publish all content under a Creative Commons license but may not be able to do so in all cases. You are responsible for ensuring that you have the necessary permission to reuse any work on this site. The Fedora logo is a trademark of Red Hat, Inc. Terms and Conditions