Previously posted on blog.labrat.info on February 2, 2011

After posting about how to make a simple firewall on a BSD system I’ve been asked to do the same for Linux. In Linux the command you’ll want to look at is iptables.

Here’s the script I use to get a basic web server protected:

#!/bin/bash

# Flush all chains
/sbin/iptables --flush

# Allow unlimited traffic on the loopback interface
/sbin/iptables -A INPUT -i lo -j ACCEPT
/sbin/iptables -A OUTPUT -o lo -j ACCEPT

# Set default policies are set to Drop
/sbin/iptables --policy INPUT DROP
/sbin/iptables --policy OUTPUT DROP
/sbin/iptables --policy FORWARD DROP

# Previously initiated and accepted exchanges bypass rule checking
# Allow unlimited outbound traffic
/sbin/iptables -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT
/sbin/iptables -A OUTPUT -m state --state NEW,ESTABLISHED,RELATED -j ACCEPT

# Allow incoming (tcp) SSH traffic
/sbin/iptables -A INPUT -p tcp --dport ssh -m state --state NEW -j ACCEPT

# Allow incoming (udp) DHCP
/sbin/iptables -A INPUT -p udp --dport bootpc -j ACCEPT

# Allow incoming (tcp) WWW request
/sbin/iptables -A INPUT -p tcp --dport www -m state --state NEW -j ACCEPT

# Drop all other traffic
/sbin/iptables -A INPUT -j DROP

We can go by this line by line.

I think at this point there is one clarification to be made. In the example I used –dport with with a name for a service and not a port number. So how did I know the names that match up to the port I’m interested in? IPTables uses the /etc/services file to match up a name to a port number. If this makes you uncomfortable you can give –dport a port number and it will work just as well.

For example if you want to open a port for Tomcat on the default port (8080) the line would look something like this:

# Allow incoming (tcp) traffic to Tomcat on port 8080
sbin/iptables -A INPUT -p tcp --dport 8080 -m state --state NEW -j ACCEPT