I’ve sweat so much over this so I thought I would share how I did it. Maybe there is already a guide somewhere or something… I asked here but we didn’t find a solution and on the DDWRT website I spent a week reading and trying before posting.
I wanted to force the PiHole to be the only accessible DNS server. Using DDWRT, I tried forcing it, but since the clients would detect that the wrong server answered the query, it didn’t work.
nslookup google.com ;; reply from unexpected source: 192.168.1.2#53, expected 18.104.22.168#53 ;; reply from unexpected source: 192.168.1.2#53, expected 22.214.171.124#53 ;; connection timed out; no servers could be reached
My firewall rules (I don’t think it changed much)
iptables -t nat -I PREROUTING -i br0 -p tcp -s ! 192.168.1.2 --dport 53 -j DNAT --to 192.168.1.2:53 iptables -t nat -I PREROUTING -i br0 -p udp -s ! 192.168.1.2 --dport 53 -j DNAT --to 192.168.1.2:53
I also tried with many iptables commands but nothing would work properly.
It would work with masquerade, but all requests looked like they were coming from the router.
iptables -t nat -A POSTROUTING -j MASQUERADE
Since I want to know which client made the request, this wasn’t an option.
I stumbled upon this reply in a post on reddit which suggested that the requests received had to go back to the router “allowing it to remove the DNAT on the reply packet”.
I was out of options so…
Note that my main network is 192.168.1.1 (br0).
I also have a public wireless network set on 192.168.10.1 (br1).
My PiHole is connected on Port 3 behind my router.
In Setup > Basic, I set Static DNS 1 to 192.168.2.2. I did not check “Use DNSMasq for DNS”
In Setup > VLANs, I assigned Post 3 to VLAN 3 (which wasn’t used).
In Setup > Networking I set the Port Setup VLAN 3 with the following:
Bridge Assignment: Unbridged
I don’t know if it does anything and I spent too much this on this issue that I won’t test without it for now but in Services:
Additional Dnsmasq Options:
interface=br0,br1 domain=local local=/local/ listen-address=192.168.2.2
Administration > Commands:
# Private network iptables -t nat -I PREROUTING -i br0 -p tcp -s ! 192.168.2.2 --dport 53 -j DNAT --to 192.168.2.2:53 iptables -t nat -I PREROUTING -i br0 -p udp -s ! 192.168.2.2 --dport 53 -j DNAT --to 192.168.2.2:53 # Public network, you don't probably need this depending... iptables -t nat -I PREROUTING -i br1 -p tcp -s ! 192.168.2.2 --dport 53 -j DNAT --to 192.168.2.2:53 iptables -t nat -I PREROUTING -i br1 -p udp -s ! 192.168.2.2 --dport 53 -j DNAT --to 192.168.2.2:53
Click Save Firewall.
Since I’m using DNS over HTTPS, a DNS leak test would reveal multiple servers if this wasn’t working.
I tested by setting my Static DNS server on my computer to 126.96.36.199.
$ nslookup duckduckgo.com Server: 188.8.131.52 Address: 184.108.40.206#53 Non-authoritative answer: Name: duckduckgo.com Address: 220.127.116.11 Name: duckduckgo.com Address: 18.104.22.168 Name: duckduckgo.com Address: 22.214.171.124
the PiHole catched the request for duckduckgo.com
DSN Leak result:
The PiHole catched everything.
I have no idea if this would be possible with wireless. I think you would need a virtual access point just for it. I also think it would draw more power or something and put more stress on the router.
Since I want my DNS server to be fast and reliable, it was already connected with a cable. It was on Port 6 though and DDWRT GUI don’t show those, So I switched.
I’m no pro, I don’t know if someone already posted this… but I couldn’t find anything in the last month regarding this issue that worked for me. Also, it’s possible there is an easier solution, but I’m a noob so idk
Hope it helps someone.
EDIT: I should’ve use ‘caught’ instead of ‘catched’ maybe? oopsie