Forcing all DNS traffic from the LAN to the firewall

This redirects the DNS queries to IPFire also.

that is what is suppose to do. Iā€™m not sure I understand the post.

I meant requests clientā€“>ipfire:53.
These are okay by definition.
You want to force requests clientā€“>8.8.8.8:53 to use IPFireā€™s DNS service, 8.8.8.8 is an example for external DNS server.

As best as I can tell it does that.

From a client (my Mac) I am sending nslookup google.com 1.1.1.1. And I see this:

If you do a nslookup google.com <ipfire-address> youā€™ll get this redirect also, which isnā€™t necessary.

If you try to add a rule with -o to the PREROUTING chain you get an error ā€œCanā€™t use -o with PREROUTINGā€.
It is correct that CUSTOMPREROUTING accept this rule but the -o will ignored because CUSTOMPREROUTING is a subchain of PREROUTING. This chain is executed before the routing decisision which determine the output nic. So the -o switch is useless.

3 Likes

That means a rule in PREROUTING isnā€™t efficient as solution for the problem
ā€œredirect all DNS queries to external DNS servers to IPFireā€
because all ā€˜well behavedā€™ queries will be redirected.

Am I right?

Guys, donā€™t forget about port 853. Which is the standard port for DNS over TLS.

1 Like

JM2C:

Since weā€™re on vacation right now its a bit difficult for me to list my current rules.

Itā€™s been a while, but I managed to make it work the way I wanted it to.

Each DNS and NTP access is processed by IPFire, no matter which DNS or NTP server is addressed - by GREEN or BLUE clients.

That means, a client can send DNS or NTP queries to any DNS or NTP server - these requests are always redirected to IPFire and answered by the servers stored in IPFire.

If it helps, I can give an overview when weā€™re back.

Best,
Matthias

P.S.: And yes, we got DNSSEC workingā€¦ :wink:

2 Likes

What Arne says would make sense, if I would get those errors. In which case the CUSTOMPREROUTING should not work at all. I however donā€™t get an error message, and the CUSTOMPREROUTING shows that the -o is working as it has set green0 as outgoing and not incoming

Jon on the other hand has it set as incoming (-i) as his screenshot shows.

Checking the my connection status on the FW, it shows that it is doing its work correctly.

As you can see, I changed 192.168.114.1 to use 9.9.9.9 as DNS, whilst 192.168.114.6 has the gateway/firewall 192.168.114.254 assigned as DNS via DHCP. The 9.9.9.9 request is intercepted and redirected to 192.168.114.254, works as advertised.

Many roads lead to Rome, or towns with similar names. Both methods seem to be doing the same thing, on the surface that is, which brings up the questions.
What is the main differences with the two approaches?
And most importantly what is the impact?

UPDATE:
I see that also the VPN clients DNS requests are redirected to the FW, which is a nice bonus. Assimilation successful ā€¦All user base are belong to us muahahahaā€¦

@arne_f my apologies to you.
You are correct. Iā€™m a muppet. :grin: I was so concerned with the IN and OUT that I failed to pay attention to the rest of the man page

The -o is not to be used with PREROUTING (custom left aside), but with FORWARD, OUT and POSTROUTING.
Why it does work is odd, and itā€™s probably only a matter of time before it would stop working or cause unforeseen problems.
Ignoring the OUT and looking at what I have which is leaving the IN on * (this means ANY) would mean that if the FW rules didnā€™t prevent DNS requests send to the FW every Tom, Dick and Harry on the Internet could sed the FW DNS requests to resolve, and the FW would merely do this. This is obviously not the aim of this exercise and most certainly not what we would like to happen.
And we donā€™t want to do any POSTROUTING packet injections or masquerading so the -o is out of place.

Jonā€™s stop rules are more elegant than my flush all.
However the start rules contain -m (ā€“match) which is only required if it is looking for a comment to match the nat rule to (for example a username or account), and as the -p (ā€“protocol) already defines the protocol this rule will apply to the -m would become redundant. Probably doesnā€™t hurt leaving it, but can be removed.

@mfischer looking forward how you got DNSSEC working.

Just to help come to a conclusion regarding the entries required, and fixing what I said earlier in the thread.
I wrote out the rules, but you can obviously shorten them with -t instead of --table, etc. Helps reading them correctly and avoid making daft mistakes like I did. :shushing_face:
My /etc/sysconfig/firewall.local entries now look as follows.

# Force DNS for green & tun to query the firewall, and not an outside DNS server
#ACCEPT from the following machine
/sbin/iptables --table nat -A CUSTOMPREROUTING --source 192.168.114.6/32 --protocol tcp --destination-port 53 -j ACCEPT
/sbin/iptables --table nat -A CUSTOMPREROUTING --source 192.168.114.6/32 --protocol udp --destination-port 53 -j ACCEPT
/sbin/iptables --table nat -A CUSTOMPREROUTING --source 192.168.114.6/32 --protocol tcp --destination-port 853 -j ACCEPT
#All others REDIRECT to FW
/sbin/iptables --table nat -A CUSTOMPREROUTING --in-interface green0 --protocol tcp --destination-port 53 -j REDIRECT --to-ports 53
/sbin/iptables --table nat -A CUSTOMPREROUTING --in-interface green0 --protocol udp --destination-port 53 -j REDIRECT --to-ports 53
/sbin/iptables --table nat -A CUSTOMPREROUTING --in-interface green0 --protocol tcp --destination-port 853 -j REDIRECT --to-ports 853

And under the stop section you would have

## add your 'stop' rules here
/sbin/iptables -t nat -F CUSTOMPREROUTING

Obviously you can also remove each entry one per line, but as all are reloaded according to the entries made, I see no reason for it, and probably avoids missing one.

Now when I do a lookup from the machine I allow

# nslookup slashdot.org 1.1.1.1
Server:		1.1.1.1
Address:	1.1.1.1#53

Non-authoritative answer:
Name:	slashdot.org
Address: 216.105.38.15

result on trackingā€¦

# conntrack -E -d 1.1.1.1 -p udp
    [NEW] udp      17 30 src=192.168.114.6 dst=1.1.1.1 sport=59234 dport=53 [UNREPLIED] src=1.1.1.1 dst=4*.***.***.**0 sport=53 dport=59234
 [UPDATE] udp      17 30 src=192.168.114.6 dst=1.1.1.1 sport=59234 dport=53 src=1.1.1.1 dst=4*.***.***.**0 sport=53 dport=59234
^Cconntrack v1.4.5 (conntrack-tools): 2 flow events have been shown.

From everyone else the same attempt will create the following track

# conntrack -E -d 1.1.1.1 -p udp
    [NEW] udp      17 30 src=192.168.114.1 dst=1.1.1.1 sport=55693 dport=53 [UNREPLIED] src=192.168.114.254 dst=192.168.114.1 sport=53 dport=55693
 [UPDATE] udp      17 30 src=192.168.114.1 dst=1.1.1.1 sport=55693 dport=53 src=192.168.114.254 dst=192.168.114.1 sport=53 dport=55693
    [NEW] udp      17 30 src=192.168.114.1 dst=1.1.1.1 sport=55694 dport=53 [UNREPLIED] src=192.168.114.254 dst=192.168.114.1 sport=53 dport=55694
 [UPDATE] udp      17 30 src=192.168.114.1 dst=1.1.1.1 sport=55694 dport=53 src=192.168.114.254 dst=192.168.114.1 sport=53 dport=55694
    [NEW] udp      17 30 src=192.168.114.1 dst=1.1.1.1 sport=55695 dport=53 [UNREPLIED] src=192.168.114.254 dst=192.168.114.1 sport=53 dport=55695
 [UPDATE] udp      17 30 src=192.168.114.1 dst=1.1.1.1 sport=55695 dport=53 src=192.168.114.254 dst=192.168.114.1 sport=53 dport=55695
^Cconntrack v1.4.5 (conntrack-tools): 6 flow events have been shown.

So we are now in the green, all is working as expected. With the exception of 192.168.114.6 every other machine on the LAN (and the VPN) have their DNS queries redirected (hijacked) and send to the FW.
For those redirected machines the DNS as defined in Network > Domain Name System will apply.

Edit Update, removed the udp/853 entry, DNS over TLS does not use udp but tcp. Watch the copy/past Gremlins sneak in that way.

2 Likes

However, I do not see the need for both entries like:

/sbin/iptables --table nat -A CUSTOMPREROUTING --source 192.168.114.6/32 --protocol tcp --destination-port 53 -j ACCEPT

/sbin/iptables --table nat -A CUSTOMPREROUTING --in-interface green0 --protocol tcp --destination-port 53 -j REDIRECT --to-ports 53

What is the reason for this, specifically the last entry?

Good point. This rule matches but redirect port 53 to port 53 which mean it does nothing.

I have to correct me!!!
-j REDIRECT always use the localhost (127.0.0.1) as target so this rule make sense. Maybee the --to-ports 53 can removed but im not sureā€¦

DNS has always been designed to use both UDP and TCP port 53, with UDP being the default, and fall back to using TCP.
If --protocol remains undefined, then all port 53 on any protocol will be redirected.

The first ACCEPT is to let the firewall know that the mentioned IP can send directly and does not get redirected.
The second entry defines the REDIRECT, to the FW (and it decides which DNS to us), instead to the destination DNS the workstation wants to us.

What are you asking that I am missing?

Hi,

I should really appreciate if someone could update the wiki to this topic accordingly.

1 Like

So this is what Iā€™ve put into firewall.local for the e.g. the green network:

iptables -t nat -A CUSTOMPREROUTING ! -o orange0 -p udp --destination-port 53 -j REDIRECT --to-ports 53
iptables -t nat -A CUSTOMPREROUTING ! -o orange0 -p tcp --destination-port 53 -j REDIRECT --to-ports 53
iptables -t nat -A CUSTOMPREROUTING ! -o orange0 -p udp --destination-port 853 -j REDIRECT --to-ports 853
iptables -t nat -A CUSTOMPREROUTING ! -o orange0 -p tcp --destination-port 853 -j REDIRECT --to-ports 853

A firewall rule which blocks all access to external DNS is in place for the green nentwork, too.

My default firewall behavior for forwarding is blocked, maybe @troll-op you additionally blocked outgoing, too which is why you need a few addtionally lines like:

/sbin/iptables --table nat -A CUSTOMPREROUTING --source 192.168.114.6/32 --protocol tcp --destination-port 53 -j ACCEPT
/sbin/iptables --table nat -A CUSTOMPREROUTING --source 192.168.114.6/32 --protocol udp --destination-port 53 -j ACCEPT

Thinking about the problem ( no output interface in prerouting, destination of request isnā€™t ipfire ) revealed the following command
iptables -t nat -A CUSTOMPREROUTING -i blue0 ! -d 192.168.20.1 -p udp -m udp --dport 53 -j REDIRECT --to-ports 53
with 192.168.20.1 == blue IP of my IPFire.
The other commands can be given accordingly.

1 Like

Alternatively, to shorten the analysis of the DNS packets, we can accept ā€˜well-behavedā€™ requests first.
So, my firewall.local reads

#!/bin/sh
# Used for private firewall rules

# See how we were called.
case "$1" in
  start)
        ## add your 'start' rules here
        iptables -t nat -A CUSTOMPREROUTING -i green0  -d 192.168.10.254 -p udp -m udp --dport 53 -j RETURN
        iptables -t nat -A CUSTOMPREROUTING -i green0  -d 192.168.10.254 -p tcp -m tcp --dport 53 -j RETURN
        iptables -t nat -A CUSTOMPREROUTING -i green0  -d 192.168.10.254 -p tcp -m tcp --dport 853 -j RETURN
        iptables -t nat -A CUSTOMPREROUTING -i green0 -p udp -m udp --dport 53 -m limit --limit 10/sec --limit-burst 20 -j LOG --log-prefix "DNSREDIRECT "
        iptables -t nat -A CUSTOMPREROUTING -i green0 -p udp -m udp --dport 53 -j REDIRECT --to-ports 53
        iptables -t nat -A CUSTOMPREROUTING -i green0 -p tcp -m tcp --dport 53 -m limit --limit 10/sec --limit-burst 20 -j LOG --log-prefix "DNSREDIRECT "
        iptables -t nat -A CUSTOMPREROUTING -i green0 -p tcp -m tcp --dport 53 -j REDIRECT --to-ports 53
        iptables -t nat -A CUSTOMPREROUTING -i green0 -p tcp -m tcp --dport 853 -m limit --limit 10/sec --limit-burst 20 -j LOG --log-prefix "DNSREDIRECT "
        iptables -t nat -A CUSTOMPREROUTING -i green0 -p tcp -m tcp --dport 853 -j REDIRECT --to-ports 853
        iptables -t nat -A CUSTOMPREROUTING -i blue0  -d 192.168.20.1 -p tcp -m tcp --dport 53 -j RETURN
        iptables -t nat -A CUSTOMPREROUTING -i blue0  -d 192.168.20.1 -p udp -m udp --dport 53 -j RETURN
        iptables -t nat -A CUSTOMPREROUTING -i blue0  -d 192.168.20.1 -p tcp -m tcp --dport 853 -j RETURN
        iptables -t nat -A CUSTOMPREROUTING -i blue0  -p udp -m udp --dport 53 -m limit --limit 10/sec --limit-burst 20 -j LOG --log-prefix "DNSREDIRECT "
        iptables -t nat -A CUSTOMPREROUTING -i blue0  -p udp -m udp --dport 53 -j REDIRECT --to-ports 53
        iptables -t nat -A CUSTOMPREROUTING -i blue0  -p tcp -m tcp --dport 53 -m limit --limit 10/sec --limit-burst 20 -j LOG --log-prefix "DNSREDIRECT "
        iptables -t nat -A CUSTOMPREROUTING -i blue0  -p tcp -m tcp --dport 53 -j REDIRECT --to-ports 53
        iptables -t nat -A CUSTOMPREROUTING -i blue0  -p tcp -m tcp --dport 853 -m limit --limit 10/sec --limit-burst 20 -j LOG --log-prefix "DNSREDIRECT "
        iptables -t nat -A CUSTOMPREROUTING -i blue0  -p tcp -m tcp --dport 853 -j REDIRECT --to-ports 853
        ;;
  stop)
        ## add your 'stop' rules here
        iptables -t nat -D CUSTOMPREROUTING -i green0  -d 192.168.10.254 -p udp -m udp --dport 53 -j RETURN
        iptables -t nat -D CUSTOMPREROUTING -i green0  -d 192.168.10.254 -p tcp -m tcp --dport 53 -j RETURN
        iptables -t nat -D CUSTOMPREROUTING -i green0  -d 192.168.10.254 -p tcp -m tcp --dport 853 -j RETURN
        iptables -t nat -D CUSTOMPREROUTING -i green0 -p udp -m udp --dport 53 -m limit --limit 10/sec --limit-burst 20 -j LOG --log-prefix "DNSREDIRECT "
        iptables -t nat -D CUSTOMPREROUTING -i green0 -p udp -m udp --dport 53 -j REDIRECT --to-ports 53
        iptables -t nat -D CUSTOMPREROUTING -i green0 -p tcp -m tcp --dport 53 -m limit --limit 10/sec --limit-burst 20 -j LOG --log-prefix "DNSREDIRECT "
        iptables -t nat -D CUSTOMPREROUTING -i green0 -p tcp -m tcp --dport 53 -j REDIRECT --to-ports 53
        iptables -t nat -D CUSTOMPREROUTING -i green0 -p tcp -m tcp --dport 853 -m limit --limit 10/sec --limit-burst 20 -j LOG --log-prefix "DNSREDIRECT "
        iptables -t nat -D CUSTOMPREROUTING -i green0 -p tcp -m tcp --dport 853 -j REDIRECT --to-ports 853
        iptables -t nat -D CUSTOMPREROUTING -i blue0  -d 192.168.20.1 -p tcp -m tcp --dport 53 -j RETURN
        iptables -t nat -D CUSTOMPREROUTING -i blue0  -d 192.168.20.1 -p udp -m udp --dport 53 -j RETURN
        iptables -t nat -D CUSTOMPREROUTING -i blue0  -d 192.168.20.1 -p tcp -m tcp --dport 853 -j RETURN
        iptables -t nat -D CUSTOMPREROUTING -i blue0  -p udp -m udp --dport 53 -m limit --limit 10/sec --limit-burst 20 -j LOG --log-prefix "DNSREDIRECT "
        iptables -t nat -D CUSTOMPREROUTING -i blue0  -p udp -m udp --dport 53 -j REDIRECT --to-ports 53
        iptables -t nat -D CUSTOMPREROUTING -i blue0  -p tcp -m tcp --dport 53 -m limit --limit 10/sec --limit-burst 20 -j LOG --log-prefix "DNSREDIRECT "
        iptables -t nat -D CUSTOMPREROUTING -i blue0  -p tcp -m tcp --dport 53 -j REDIRECT --to-ports 53
        iptables -t nat -D CUSTOMPREROUTING -i blue0  -p tcp -m tcp --dport 853 -m limit --limit 10/sec --limit-burst 20 -j LOG --log-prefix "DNSREDIRECT "
        iptables -t nat -D CUSTOMPREROUTING -i blue0  -p tcp -m tcp --dport 853 -j REDIRECT --to-ports 853
        ;;
  reload)
        $0 stop
        $0 start
        ## add your 'reload' rules here
        ;;
  flush)
        iptables -t nat -F CUSTOMPREROUTING
        ;;        
  *)
        echo "Usage: $0 {start|stop|reload}"
        ;;
esac
1 Like

@hellfire
I think you are looking at the wrong part of the thread, have another look here

From what I see your lines are for orange0 and not green0 and you are still using the ! -o which as @arne_f correctly pointed out was incorrect, and does not apply to PREROUTING, and therefore also not to CUSTOMPREROUTING.

For example your line
iptables -t nat -A CUSTOMPREROUTING ! -o orange0 -p udp --destination-port 53 -j REDIRECT --to-ports 53
should read
iptables -t nat -A CUSTOMPREROUTING -i green0 -p udp --destination-port 53 -j REDIRECT --to-ports 53

The reason I have the ACCEPT CUSTOMPREROUTING rule before the above mentioned REDIRECT CUSTOMPREROUTING was to show what is needed if you have a specific machine that should have access to whatever DNS server it wants to use and not force it to REDIRECT to the one used by the FW.
In my example 192.168.114.6/32 is the single IP machine, and as you can see from the conntrack output it chats to 1.1.1.1 via dst=4*.***.***.**0 which is red0
The second conntrack shows that the machine 192.168.114.1 which does not have an ACCEPT entry is REDIRECT to 192.168.114.254 which is green0 and it does the DNS queries.
In the end 192.168.114.1 believes it spoke to 1.1.1.1, but actually 192.168.114.254 did the resolve with whichever DNS server was assigned in Network > Domain Name System via the Web GUI.

@bbitsch
Do I understand you correctly? I should add a destination, -d 192.168.114.254 (in my example) to shorten the query times and streamline everything, and that the FW is also the DNS Proxy Server is irrelevant?

PS I tend to write explanations about why I say something not because I think you have no clue, but more so that newer users who donā€™t know can understand why. Please do not take officeā€¦ :nerd_face:
I treat everyone like a special mushroom :kissing_heart:

1 Like