Force all devices to use local Adguard DNS

Hi,

I am using Adguard in my HomeNetwork to filter DNS. Working good for my DHCP Devices. But If I specify my DNS explicit on a machine, I can bypass the Adguard and use the DNS Server directly.
I want to redirect all DNS traffic through my Adguard.

I added the following, but it seems not to work (tested with https://www.dnsleaktest.com/)

/ip firewall nat 
add chain=dstnat action=dst-nat to-addresses=192.168.10.4 protocol=udp src-address=!192.168.10.4 dst-address=!192.168.10.4 dst-port=53 
add chain=dstnat action=dst-nat to-addresses=192.168.10.4 protocol=tcp src-address=!192.168.10.4 dst-address=!192.168.10.4 dst-port=53 
add chain=srcnat action=masquerade protocol=udp src-address=192.168.10.0/24 dst-address=192.168.10.4 dst-port=53 
add chain=srcnat action=masquerade protocol=tcp src-address=192.168.10.0/24 dst-address=192.168.10.4 dst-port=53



10.4

is my Adguard

Am I missing something?
Thanks!

Seems 100% correct to me!

The only thinkable way they are no using the rules (are the counters going up?) is, they are not using this router for DNS. At least not for DPort 53 (do they use some DoH stuff)?

For ip dhcp-server networks. on user subnets save the one the server is on…

subnet A dns-server=192.168.10.4
subnet B dns-server=192.168.10.4
subnet C (same subnet as server) dns-server=gatewayIP of subnet

Then…
/ip firewall nat
add chain=dstnat action=dst-nat in-interface-list=LAN src-address-list=!exclude-adguard protocol=udp dst-port=53 action=dst-nat to-addresses=192.168.10.4
add chain=dstnat action=dst-nat in-interface-list=LAN src-address-list=!exclude-adguard protocol=tcp dst-port=53 action=dst-nat to-addresses=192.168.10.4

where firewall address list ‘exclude adguard’ includes the adguard server itself and perhaps some other users?)

if its only the adguard server itself that needs to be excluded, then,
/ip firewall nat
add chain=dstnat in-interface-list=LAN src-address=!192.168.10.4 protocol=udp dst-port=53 action=dst-nat to-addresses=192.168.10.4
add chain=dstnat in-interface-list=LAN src-address=!192.168.10.4 protocol=tcp dst-port=53 action=dst-nat to-addresses=192.168.10.4

In summary your rules are correct for dst nat, there should be no need for your extra sourcenat rules!

I learned it from you @anav! and, wanted to help, obviously you were faster :slight_smile:

@bastiitsab what @anav said is fully transparent for user, so on the PC where you configure custom DNS, and wants to use dig/nslookup, you will see the response from the custom DNS which you configured - which is not true, just saying…

Without network schema… the adguard is on separate network port on the routerboard or is connected to one remote switch with other devices?

Without the SNAT-rules, the whole concept wont work (assuming the DNS-Server is in the same (V)LAN as the DNS-Client)!!

I disagree, one only needs the dst-nat rules, what IS NEEDED that should be noted is firewall forward chain rules.

add chain=forward action=accept in-interface-list=LAN dst-address=LANIP-of_Adguard_Server

assuming all the vlans are members of the interface list LAN

( @anav: hi :wink: )


As usual, without diagram or at least one detailed description, all is useless…

Assuming the client tries to contact 8.8.8.8, the DNAT-rule catches the frame and forwards it to 192.168.10.4.
The DNS-server will process the request and … what will happen, my dear ANAV!!!

The IP-Stack of the server will send the frame back to the source-IP of the inital frame. Someting out of the 192.168.10.0/24 network. The (inital) client will see a DNS-packet coming from 192.168.10.4. But he contacted 8.8.8.8. This will become invalid and gets silently dropped.

The only way to fix this is an additional SNAT rule which makes the DNS-server send the frame back to the router (insted of directly to the client). The Router will undo the DNAT/SNAT and for the client the DNS-answer is from 8.8.8.8 (but it was processed by 192.128.10.4).

Thats a typically asymmetric fordwaring scenario, nasty stuff to find.

Not the way I see it.
The DNS server be it pihole or adguard with simply go out the internet from there and return the result to the correct lan user.

Instead of user ----> dhp-server network dns setting OR router dns OR ipv4 PC injected DNS site → internet
user----> adguard ----> internet

My two cents. Maybe you can do without the SNAT rule only if the DNS server is the router itself (set in the DHCP server configurations) which in turn points to the Pihole’s IP.

What you all (except anav, obviously) don’t understand is that the masquerade (or srcnat) is supposed to be done already before,
in fact why the hell would I want to resolve DNS for internal devices on AdGuard, if not to filter traffic on INTERNET???

So incontrovertibly (with the details provided by the OP) the srcnat rules are of no use at all,
because the LAN traffic is already being masqueraded from another rule, and connection-tracking facility do it’s work.

Its OK, you see it worng, but “a man’s mind is his kingdom”.
For all other, thats exactly the behaviour without a SNAT rule:

Screenshot 2022-11-25 215211.jpg
Outbonud: 10.88.10.1 → 8.8.8.8
Inbound: 10.88.30.21 → 10.88.10.1

The answer form 10.88.30.21 is invald, because an answer from 8.8.8.8 is awaited.

where are two LAN on OP??? only one…
why aren’t all the NAT rules present but only the four ones?
it is “impossible” that only those 4 rules exist.
All of this is based on the fact that rude OPs like this one, who doesn’t even deign to answer, don’t write any relevant details…

IT IS OBVIOUS that the masquerade (srcnat) is already done for everything in output, already before those rules,
otherwise what the f—k do I resolve them to do the DNS, if I can’t navigate there???

Listen to self-proclaimed NAT expert (me) if you don’t want to listen to someone else who’s also right. :slight_smile:

When there’s one common subnet for client and Adguard, you must have some (*) srcnat that aplies to redirected traffic, otherwise it won’t work.
When there are different subnets for client and Adguard, you don’t need any extra srcnat.

(*) Some previously existing rule may apply, be it one for hairpin NAT, or sort of invalid too broad unconditional masquerade. But there must be something, unless Adguard machine recognizes these redirected requests and sends responses to router instead of directly to client’s internal address.

Well thats too vague of a response.

Condition 1 - many vlans and one separate vlan where adguard or DNS server resides… - covered, no need for sourcenat

Condition 2 - only one LAN subnet and users and adguard/dns server device are on same subnet. - covered, need sourcenat says you and one other yahoo.

Condition 3 - many vlans and the adguard/dns device is on a vlan that also contains users that should go through adguard/dns server.

So we have a situation where 3 has not been fully explored but it has traces of both conditions 1 and 2 in it.

Personally I will be adamant that you dont need sourcenat regardless of location, you have not shown why… just telling me its so, carries no water LOL

Ex. vlans 10,20,30,40, 50, and they all belong to the interface list of LAN.

  • vlan 50 contains adguard/dns server on 192.168.50.50, vlan 20 needs to use regular DNS from router
  • Firewall address list called “excluded” includes 192.168.20.0/24 AND 192.168.50.50

Step 1.
/ip dhcp-server network
add address=192.168.10.0/24 gateway=192.168.10.1 dns-server=192.168.50.50
add address=192.168.20.0/24 gateway=192.168.20.1 dns-server=192.168.20.1
add address=192.168.30.0/24 gateway=192.168.30.1 dns-server=192.168.50.50
add address=192.168.40.0/24 gateway=192.168.40.1 dns-server=192.168.50.50
add address=192.168.50.0/24 gateway=192.168.50.1 dns-server=192.168.50.1

Step2.
input chain rules.
add chain=input action=accept in-interface-list=LAN dst-port=53 protocol=tcp
add chain=input action=accept in-interface-list=LAN dst-port=53 protocol=udp

forward chain rules
add chain=forward action=accept in-interface-list=LAN dst-address=192.168.50.50

Dst Nat rules
add chain=dstnat action=dst-nat in-interface-list=LAN src-address-list=!excluded dst-port=53 protocol=tcp to-addresses=192.168.50.50
add chain=dstnat action=dst-nat in-interface-list=LAN src-address-list=!excluded dst-port=53 protocol=udp to-addresses=192.168.50.50

Src Nat rules
not required, but who knows I could be wrong its happened before…once. :wink:

Think about this: You know hairpin NAT, commonly used when you have public address on your router, dstnat (forwarded ports) from there to some internal server, and you want client in same LAN to connect to this server using public address on router, right? And you surely know that it doesn’t work by default, you have to add srcnat rule that changes source of these connections to (most often) router’s internal address. Now what’s the difference between redirecting connections to and connections to 8.8.8.8? The latter is few more hops away, but other than that (because it doesn’t matter when you redirect it anyway)? The answer is “none”. So it doesn’t work by default and you need srcnat to fix it.

Hmmm, will have to ponder…I can see that we are sending traffic to a local destination and hairpin nat applies to a server within the same subnet…
So its not a phenomena that is only valid with attemping to use the public IP of the router to direct user…
I didnt think of it as using 8.8.8.8 etc as the local wanIP analogy… even though Guscht stated so directly
I also thought for some reason the adguard server kept track of originators etc…

I understand in hairpin where the router shortcuts the sourceip address but the user is expecting the response from a differnt IP and just drops the return, just dont see how it happens here but oh well…

so we need something like???
add action=masquerade chain=srcnat dst-address=adbuard subnet src-address=adguard subnet

Which now makes Guscht’s explanation more clear and who I owe an apology for being bang on the money.
Yes it is nasty stuff LOL. I call it mind pretzel.

Yes, I think so. I have a similar rule and it works both for the hairpin NAT and dns redirect

thanks broderick I see the original poster was more specific/accurate and hairpin natted only for the specific port which is probably better.