Backend mismatches make firewall checks look empty or contradictory when one command reads the legacy iptables API and another reads nftables compatibility rules. The version suffix on the iptables command shows which backend automation or an administrator is about to inspect.
iptables can be delivered as the legacy command or as the xtables-nft compatibility command, which accepts iptables syntax while storing rules through the nf_tables kernel API. The active command reports either (legacy) or (nf_tables), and Debian or Ubuntu hosts usually expose the selected implementation through update-alternatives.
Version, alternatives, and inventory commands read state only. They do not switch alternatives, flush rules, or install a new firewall stack, so use the matching iptables-save, iptables-legacy-save, iptables-nft-save, or nft command only after the active backend is known.
Steps to check the active iptables backend:
- Print the active IPv4 iptables backend.
$ iptables --version iptables v1.8.11 (nf_tables)
(nf_tables) means the command uses the nftables compatibility backend. (legacy) means the command uses the older legacy kernel API.
- Check the IPv6 command separately when the host has IPv6 firewall rules.
$ ip6tables --version ip6tables v1.8.11 (nf_tables)
iptables and ip6tables usually follow the same backend on Debian and Ubuntu hosts, but checking both avoids reading IPv4 and IPv6 rules through different command families.
- Inspect the selected alternative on Debian or Ubuntu hosts.
$ update-alternatives --display iptables iptables - auto mode link best version is /usr/sbin/iptables-nft link currently points to /usr/sbin/iptables-nft link iptables is /usr/sbin/iptables slave iptables-restore is /usr/sbin/iptables-restore slave iptables-save is /usr/sbin/iptables-save /usr/sbin/iptables-legacy - priority 10 slave iptables-restore: /usr/sbin/iptables-legacy-restore slave iptables-save: /usr/sbin/iptables-legacy-save /usr/sbin/iptables-nft - priority 20 slave iptables-restore: /usr/sbin/iptables-nft-restore slave iptables-save: /usr/sbin/iptables-nft-save
If the command is managed by alternatives, the line that says currently points to should match the backend shown by iptables --version.
- Read the active filter table through the current iptables command.
$ sudo iptables -S -P INPUT ACCEPT -P FORWARD ACCEPT -P OUTPUT ACCEPT
This reads the backend selected by the plain iptables command. Use sudo iptables-legacy -S or sudo iptables-nft -S only when deliberately checking a backend that is not currently selected.
- Dump restore-format rules from the active backend when a full ruleset inventory is needed.
$ sudo iptables-save # Generated by iptables-save v1.8.11 (nf_tables) on Fri Jun 5 21:45:09 2026 *filter :INPUT ACCEPT [0:0] :FORWARD ACCEPT [0:0] :OUTPUT ACCEPT [0:0] -A INPUT -p tcp -m tcp --dport 22 -j ACCEPT COMMIT # Completed on Fri Jun 5 21:45:09 2026
A host with no rules in the selected backend may return no output from iptables-save. In that case, iptables -S still confirms the selected filter table policies.
- Compare the native nftables view only when the version suffix says (nf_tables).
$ sudo nft list ruleset table ip filter { chain INPUT { type filter hook input priority filter; policy accept; tcp dport 22 counter packets 0 bytes 0 accept } }When iptables reports (nf_tables), matching rules can appear through both iptables-save and nft list ruleset. When iptables reports (legacy), native nft output may be empty even though legacy iptables rules exist.
Mohd Shakir Zakaria is a cloud architect with deep roots in software development and open-source advocacy. Certified in AWS, Red Hat, VMware, ITIL, and Linux, he specializes in designing and managing robust cloud and on-premises infrastructures.