How to configure a firewall on Debian-ish system

From PeerFreedom Wiki
Jump to navigation Jump to search

Instalation

Install necessary package:

# apt-get install nftables

Enable start at boot:

# systemctl enable nftables.service

Make system use nftables by default instead of iptables:

# update-alternatives --set iptables /usr/sbin/iptables-nft
# update-alternatives --set ip6tables /usr/sbin/ip6tables-nft
# update-alternatives --set arptables /usr/sbin/arptables-nft
# update-alternatives --set ebtables /usr/sbin/ebtables-nft

Example config

Nftables config is in /etc/nftables.conf

Here is stateful example with IP whitelist:

#!/usr/sbin/nft -f

flush ruleset

table inet filter {
        chain input {
                type filter hook input priority 0; policy drop;
                ct state established,related accept
                iif "lo" accept
                ct state invalid log prefix "Invalid packet: " drop
                ip protocol icmp accept
                ip protocol igmp accept
                ip6 nexthdr ipv6-icmp accept
                udp dport 0-65535 ct state new jump UDP
                tcp dport 0-65535 tcp flags & (fin | syn | rst | ack) == syn ct state new jump TCP
                udp dport 0-65535 log prefix "UDP reject: " reject
                tcp dport 0-65535 log prefix "TCP reject: " reject with tcp reset
                ip protocol != { tcp, udp, icmp } log prefix "Other IPv4 reject: " reject with icmp type prot-unreachable
                log prefix "Other reject: " reject with icmpx type admin-prohibited
        }

        chain forward {
                type filter hook forward priority 0; policy drop;
                #clamp mss to pmtu
                meta l4proto tcp tcp flags & (syn|rst) == syn counter packets 0 bytes 0 tcp option maxseg size set rt mtu
                ct state established,related accept
                ct state invalid log prefix "Invalid forward packet: " drop
                #docker
		mark 1 accept
		#example forward connection to 10.0.0.0/24 subnet on LAN interface eth0
		iifname "eth0" ip saddr 10.0.0.0/24 accept
		#example forward some tcp and udp ports to 10.0.0.5 client on LAN eth0
        	#oifname "eth0" ip daddr 10.0.0.5 tcp dport { 22, 80, 443 } accept
        	#oifname "eth0" ip daddr 10.0.0.5 udp dport { 60000-61000 } accept
		log prefix "Other forward reject: " reject with icmpx type host-unreachable
        }

        chain output {
                type filter hook output priority 0; policy accept;
        }

        chain UDP {
                #put open UDP ports here
                #example with ports range 60000-61000 for mosh
                #mosh
                #udp dport { 60000-61000 } accept
        }

        chain TCP {
                #put open TCP ports here
                #example with few selected ports
                #http(s)
                #tcp dport {80, 443} accept        

                #example with port by service name, it equals port 22
                #ssh
                #tcp dport { ssh } accept

                #example with one port, but with IP whitelist
                #netdata
                #tcp dport 19999 jump accept-if-trusted

                #example with one open port
                #irc
                #tcp dport 6667 accept

        }

        chain accept-if-trusted {
                # put trusted IP addresses here:
                # for some services (e.g. ssh), if in chain TCP you given jump "accept-if-trusted" instead "accept",
                # then this ssh TCP will be accepted only from this IPs here
                
                #single IPv4 address example
                #ip saddr 172.16.0.2 accept

                #trusted IPv4 subnet example               
                #ip saddr 192.168.2.0/23 accept

                #single IPv6 address example
                #ip6 saddr 2001:db9::dead:beef accept

                #trusted IPv6 subnet example
                #ip6 saddr 2001:db8::/32 accept
        }

}

# NAT - needed only if:
# 1) you provide internet (e.g. you are the Internet Gateway in a LAN)
# 2) maybe some VM types
table ip nat {
        chain prerouting {
                type nat hook prerouting priority 0; policy accept;
                #example forward some ports to client 10.0.0.5
		#tcp dport { 22, 80, 443 } dnat 10.0.0.5
		#udp dport { 60000-61000 } dnat 10.0.0.5
        }

        chain postrouting {
                type nat hook postrouting priority 100; policy accept;
                #example forward ppp0 interface to 10.0.0.0/24 subnet
		#ip saddr 10.0.0.0/24 oifname "ppp0" masquerade
        }
}

# docker - probably needed if you user docker
table ip filter {
  chain DOCKER-USER {
    mark set 1
  }
}

Basic commands

Start firewall:

# systemctl start nftables.service

Stop firewall:

# systemctl stop nftables.service

Restart firewall:

# systemctl restart nftables.service

Empty firewall rules:

# nft flush ruleset

List rules:

# nft list ruleset

More resources