Iptables is a packet filter included in most modern Linux distributions. It includes a lot of useful advanced features to do almost anything necessary at the firewall level, but this tutorial will focus on the basics.

All iptables rules are created and modified via passing command-line options to the iptables binary. There are also GUI utilities in some distributions to do this, but they tend to be much less powerful. For this demo, you must have permission to run iptables as root via sudo. The TAs should be able to do this on netsec-demos but you may want to try it on your own machine.

Iptables saves any rules you create only until the computer is rebooted, and so another solution is needed for permanent rule storage. Most distributions handle this by including two scripts, iptables-save and iptables-restore. The tutorial will not worry about saving rulesets.

Rule Basics

Iptables operates based on rules. The rules are applied top-down, with the first match being used. Therefore, more specific rules should be placed above more general rules. For example, a rule to allow all SSH packets should be above/before a rule to reject all packets, so that SSH connections are allowed, but nothing else. Each rule is specified by running the iptables binary with the desired switches.

The switches specify first what table and chain a rule applies to, what packet characteristics it applies to, and to what target it should jump after determining that there is a match.

Tables and Chains

Iptables allows for different tables and chains. There are three main tables: filter, nat, and mangle. Each table has chains specific to their functions.

Users can also append new chains with special rules for different purposes. For example, in Redhat-based distributions, the GUI firewall configuration generates a custom input chain to separate GUI-generated rules from user-created rules.

filter is the default table if none is specified; this table parses all packets eventually regardless of what we do, and exists to drop or accept packets based on their characteristics. It includes 3 chains by default: INPUT, OUTPUT, and FORWARD. These chains act upon inbound, outbound, and forwarding packets (ie, when the current host is acting as a router).

nat handles network address translation, and includes two chains: prerouting and postrouting. This allows us to change the source or destination addresses based on packet characteristics. Two very common uses of this table is to allow for port forwarding or sharing an internet connection.

mangle includes the chains in both of the other tables, and allows for altering packet fields such as TOS, TTL, etc.

Command Line Options

Rule Specifications

When adding rules, switches must be used to specify what constitutes a match. The most typical switches typically match based on port, IP address, protocol, and connection state.

These are specified via the following switches:

Iptables uses the -m switch to allow for extended matching. This allows the use of specific extensions. A commonly used one is state, which allows for connection tracking.

For example, this allows us to allow only established packets inbound (ie, those that are not SYN packets for TCP), to ensure that we can always connect out but nobody else can initiate inbound connections.

Here are some common ways to use -m state:


All rules must end with a target to jump to. This specifies what to do when a rule does match.

Here are some common targets (Not all of these can be used with all tables):

Things to Try

If you have your own VM with root access, try setting up a firewall with these commands. This will help in getting famililar with writing firewall rules. Everyone should do the classwork section though- that is the part that will be taken for a grade.

To start, try setting up your machine to only allow connections to a local netcat server with the following options, and run nmap against your machine.

Establish a netcat server with the following:

nc -l -p 2500

Ensure that your iptables rules are cleared out:

iptables -F

Make sure not to block your own ssh traffic:

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

Set the INPUT policy to drop all inbound packets:

iptables -P INPUT DROP

Notice that this will prevent you from connecting outbound. (Try downloading a webpage.) Why? Response SYN-ACKs and DNS responses from remote servers are also dropped, along with all other inbound packets. Next, let's allow all related and established packets to come in, so that we can make outbound connections.

iptables -A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT

Now you should be able to visit websites, etc, but nobody externally will be able to initiate a connection to your netcat server. You can try to connect to your own machine with nc localhost 2500.

To allow connections to your server, add another rule to allow SYN packets with a destination port of 2500.

iptables -A INPUT -p tcp -m state --state NEW --dport 2500 -j ACCEPT

Other rules to experiment with are those such as the following, which port forwards port 2500 to another address:

iptables -A FORWARD -d <destinationip> -p tcp --dport 2500 -j ACCEPT
iptables -A PREROUTING -p tcp --dport 2500 -j DNAT --to-destination <destinationip>:2500


Complete the following tasks and check out with TAs.

Part A

For this part of the assignment, you will configure a firewall. Your rules will be in the format of iptables command-line switches, in the order that you want them to be applied.

Put your rules in iptables.rules. There is one sample rule to demonstrate the format, which simply drops all inbound packets (cutting off all communication.)

Your firewall must do the following:

Part B

For the second part of the assignment, you will write snort rules to detect the fictional Simple Worm.

Your rules should do the following:

This link contains all you need to know about Snort.

Extra Credit

Deploy part A and part B on your own linux VM, test the rules and show the results to instructors. If you have a Linux VM, you need two additional steps to configure:

  1. Install snort;
  2. Confgure network setting to ensure the host and VM can communicate with each other (i.e., can ping each other).

If you would like to install a new VM for this lab, we prepare one based on Kali Linux, which is the most popular Ethical hacking linux distribution and comes with a bunch of hacking tools installed. Here are the steps to install this configured VM (of course, you can download and install the latest Kali VM version and configure iit by yourself.).

  1. Install VirtualBox 5.4. on your laptop.
  2. Create a Host-only network: Preferences -> Network -> Host-only Networks -> Add host-only network.
  3. Copy the image from the following path on hamsa to your laptop: /home/shared/firewall-lab-vm-kali-64bit.ova
  4. Double clikc the file to install the VM.
  5. Disable USB 2.0 Controller in the VM settings.
  6. Start and login the VM with the folllowing credential: username: root password: toor
  7. Make sure your host and the VM can communicate with each other. If not, select the network as Host-only mode.
  8. Work on the lab in VM and additional notes are availablein /root/firewalls/ folder.
  9. Test the your rules by making connections from your host machine (using netcat or telnet) to the VM.