Deny all incoming connections with iptables?

I want to make some simple iptables rules to deny all incoming connections and allow outgoing. How can I do that?


Try this with root access :

# Set default chain policies
iptables -P INPUT DROP
iptables -P FORWARD DROP
iptables -P OUTPUT ACCEPT

# Accept on localhost
iptables -A INPUT -i lo -j ACCEPT
iptables -A OUTPUT -o lo -j ACCEPT

# Allow established sessions to receive traffic
iptables -A INPUT -m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPT

Note that this will brutally cut all running connections - this includes things like the SSH connection you may use to administer the server. Only use this if you have access to a local console.

See Miphix' answer for how to add an exception for SSH.


If you’re working remotely via SSH, you might want to add this (-I inserts it before all other rules in INPUT):

iptables -I INPUT -p tcp --dport 22 -j ACCEPT

If your SSH service is listening on another port, you’ll have to use that port instead of 22.

Otherwise, you might accidentally lose access.


Be aware that the other answers do not cover IPv6! If your system accepts IPv6 traffic, not a single iptables rule will apply to ipv6 traffic.

instead of using iptables / ip6tables directly, i recommend using iptables-restore and save. These tools allow to specify a iptables configuration with multiple rules and easily load it with one command.

create a file (i named it iptables.rules) with the following content:

*filter

# drop forwarded traffic. you only need it of you are running a router
:FORWARD DROP [0:0]

# Accept all outgoing traffic
:OUTPUT ACCEPT [623107326:1392470726908]


# Block all incoming traffic, all protocols (tcp, udp, icmp, ...) everything.
# This is the base rule we can define exceptions from.
:INPUT DROP [11486:513044]

# do not block already running connections (important for outgoing)
-A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT

# do not block localhost
-A INPUT -i lo -j ACCEPT

# do not block icmp for ping and network diagnostics. Remove if you do not want this
# note that -p icmp has no effect on ipv6, so we need an extra ipv6 rule
-4 -A INPUT -p icmp -j ACCEPT
-6 -A INPUT -p ipv6-icmp -j ACCEPT

# allow some incoming ports for services that should be public available
-A INPUT -p tcp -m tcp --dport 22 -j ACCEPT
-A INPUT -p tcp -m tcp --dport 80 -j ACCEPT
-A INPUT -p tcp -m tcp --dport 443 -j ACCEPT

# commit changes
COMMIT

Note i have added some extra example if you want to allow ICMP and traffic to specific ports.

now you can load it with these commands:

iptables-restore < iptables.rules
ip6tables-restore < iptables.rules

Now your rules cover also ipv6 and are easy to manage.

Additional note to Debian users: if you are satisfied with your rules, you can apt install iptables-persistent so the rules get restored after reboot. The rules are not auto-saved on shutdown, so run netfilter-persistent save to update the persistent rules.