Skip to main content

Why nftables

By January 4, 2020September 12th, 2022No Comments

You may be thinking, “Why nftables”. In this blog we hope to go some way in answering that question. If nothing else you how to build a very simple firewall with iptables, ip6tables and then nftables. To persist firewall rules created with nftables take a look at this blog.

New to Red Hat Enterprise Linux 8 is the firewall module nftables and you may think that iptables have served you well for many years so why nftables. Firstly, and what we demonstrate in this blog and video we look at the pan-protocol aspect, we can configure one rule to work with both IPv4 and IPv6 rather than having to write different rules with iptables and ip6tables. This becomes a major concern as it is easy to overlook unused protocols. Secondly, nftables does not have any defines tables or chains, you create everything. Whilst this may seem a pain after initially, the advantage comes from the resource utilisation. If you only need the filter table and input chain then that is all you need to consume memory.

For the demonstration we build an over-simple firewall that allows only inbound SSH traffic and nothing else. Using CentOS 8, firewalld will be loaded by default with associated nftables rules. We start by clearing this:

# systemctl disable --now firewalld
# nft flush ruleset

This done, we should be able to test access via ICMP to ping. This will work on both IPv4 and IPv6:

# ping
# ping ::1

Now we will look at what happens if we use just iptables to block the ICMP requests whilst allowing SSH:

# iptables -A INPUT -p tcp --dport 22 -j ACCEPT
# iptables -A INPUT -j DROP

This will block the ping to on IPv4 but not to ::1 on IPv6. This is a major reason why nftables! We need just a single rule set but using the native tools we have to duplicate the ruleset in IP6tables.

# ip6tables -A -p tcp --dport 22 -j ACCEPT
# ip6tables -A - j DROP

With two rulesets we have now blocked the required traffic to the system on both IPv6 and IPv4. Using nftables we need just one ruleset:

# nft add table inet filter
# nft add chain inet filter INPUT { type filter hook input priority 0\; policy accept \; }
# nft add rule inet filter INPUT tcp dport 22 accept
# nft add rule inet filter INPUT drop

The one rule set will now work with both version of IP and our memory utilisation is reduced as we only use nftables and only the one table and chain.

Online Instructor-led training