I very much enjoy my homelab projects, from VMware ESXi, Synology, FreeNAS, pfSense, MikroTik, Ubiquiti/Unifi, they all have played an important role in developing my skills in various facets of IT – networking, security, virtualization, storage, etc. I don’t use all of these technologies at the work place, but I do use the standard concepts and practices from each platform, which has been paramount to my learning. Out of all of these platforms, none for me has been as advantageous, economically cheap, or simple to implement for DNS filtering than Pi-hole on the Raspberry Pi. In my opinion, the benefits far exceed the time and costs, and I highly recommend this solution to any IT administrator/technicain or tech savvy users interested in implementing a DNS filter for their private network that is backed by an awesome development team and community of supporters, such as my self.
What is Pi-hole?
Simply put, Pi-hole is Linux based network-level advertisement and tracker blocking application. It can be installed on a Raspberry Pi, Linux machine (virtual machines included), and cloud implementations are also possible. Once installed, it can block advertisements and trackers for all devices on your entire network, simply point your devices DNS to the Pi-hole’s IP on your private network. Pi-hole is best known for blocking advertisements and trackers, but it is not restricted to these two categories alone, Pi-hole can block any DNS. For example, there are numerous DNS block lists available that can be added to the Pi-hole to block known malicious DNS addresses, and so it is not only about the convenience of blocking advertisements and trackers, but for security as well. Pi-hole comes with a polished web GUI, but access via terminal is available as well. I personally prefer the GUI for minor changes, but use the terminal for any large/sweeping changes or real-time monitoring, such as clearing the database, adding large amounts of DNS entries to the lists, or simply tailing the DNS logs.
A Polished Web Interface
As previously mentioned, Pi-hole utilizes a polished web interface that has developed over time with each release. Terminal access is available and I would recommend learning both. The entire installation is done via terminal, although it is wizard driven. I’ve taken a few screenshots with descriptions below.
My Homelab Setup: Two Is Better than One (DNS Failover)
At home, I run two Raspberry Pi’s with Pi-hole installed on each. Pi-hole1 is primary, while Pi-hole2 is fail-over. This setup uses rules specified in my MikroTik router (model: CCR1009-7G-1C-1S+) that detects when Pi-hole1 is offline. When Pi-hole1 is offline the router immediately clears the routing table for traffic going to Pi-hole1 and redirects all new traffic to Pi-hole2, until Pi-hole1 is no longer offline. In addition, all DNS traffic is always routed through one of the two Pi-holes. Google devices, such as Google Chromecast and some Android devices have Google’s DNS (18.104.22.168 etc.) hard-programmed into the software and in many cases the DNS address cannot be modified. It is good practice to setup NAT forwarding rules to redirect all traffic to the Pi-hole that is not already destined to the Pi-hole over DNS port 53. Doing this, will also ensure that users on the network do not bypass the Pi-hole’s security by entering in their own static address on their device.
There may be a time when you will want a device to bypass the Pi-hole, if this is the case, then (if your router supports it) an address/group list of some kind will need to be created and populated with the IP of the devices/clients you would like to have bypass the DNS redirection to the Pi-hole. MikroTik routers support Address Lists, which in this case is quite easy to implement. For MikroTik’s, the following rule will ignore the IP addresses of the devices/clients in the “Pi-hole Redirection Ignore” Address List and force all other local DNS traffic (UDP/TCP over port 53) on the private network that is not destined to the Pi-hole (!10.10.100.2) to be redirected to the Pi-hole (10.10.100.2).
/ip firewall nat add action=dst-nat chain=dstnat comment="Redirect Private DNS (UDP) - Pi-hole1." dst-address=!10.10.100.2 dst-port=53 in-interface=Bridge-Local log=yes log-prefix="Redirect_Private DNS (UDP)" protocol=udp src-address-list="!Pi-hole DNS Redirection Ignore" to-addresses=10.10.100.2 add action=dst-nat chain=dstnat comment="Redirect Private DNS (TCP) - Pi-hole1." dst-address=!10.10.100.2 dst-port=53 in-interface=Bridge-Local log=yes log-prefix="Redirect_Private DNS (TCP)" protocol=tcp src-address-list="!Pi-hole DNS Redirection Ignore" to-addresses=10.10.100.2
…and depending on your particular network setup. A masquerade rule may be required:
/ip firewall nat add action=masquerade chain=srcnat comment="Masquerade DNS (UDP) - Pi-hole1." disabled=yes dst-address=10.10.100.2 dst-port=53 log=yes log-prefix="Masq_Private DNS (UDP)" out-interface=Bridge-Local protocol=udp add action=masquerade chain=srcnat comment="Masquerade DNS (TCP) - Pi-hole1." disabled=yes dst-address=10.10.100.2 dst-port=53 log=yes log-prefix="Masq_Private DNS (TCP)" out-interface=Bridge-Local protocol=tcp
My Homelab Setup: The Hardware
Last but not least is the hardware. I’m currently using two of the following: Raspberry Pi 3 B+ w/ NovaLabs POE Hat for Power Over Ethernet via Unifi POE Switch. These components are mounted in a custom 3D printed Raspberry Pi ventilated case /w a 40mm top mounted fan for cooling and black nylon nuts/bolts to complete the build.