I recently read about a neat method of measuring traffic with iptables on linux hosts, which is nice for pentesting or infrastructure debugging. This is a rather short post describing that approach.

Benefits of using iptables for traffic measurements

  1. One nice thing about iptables is that it is very likely to be present on any linux server/client you run, so you dont need to install any extra packages.
  2. For infrastructure debugging/planning purposes you might need to know quickly how much traffic flows between 2 specific hosts/ports/… . Maybe you do not have monitoring in place yet or the monitoring is not fine grained enough (e.g., aggregating ALL packets on host interfaces).
  3. In pentesting this is a fast and easy method to measure how much traffic/attention your operation produces.

Hands-on Example

Let us assume we want to quickly measure the traffic between the current machine and a remote host.

Initially, we have empty iptables chains:

~# iptables -L
Chain INPUT (policy ACCEPT)
target     prot opt source               destination         

Chain FORWARD (policy ACCEPT)
target     prot opt source               destination         

Chain OUTPUT (policy ACCEPT)
target     prot opt source               destination

Of course some servers might already have rules attached and we do not want to mess with them. We create a new chain dedicated for our measurements:

~# iptables -N TARGET
~# iptables -L
Chain INPUT (policy ACCEPT)
target     prot opt source               destination         

Chain FORWARD (policy ACCEPT)
target     prot opt source               destination         

Chain OUTPUT (policy ACCEPT)
target     prot opt source               destination         

Chain TARGET (0 references)
target     prot opt source               destination

Now we attach measurement rules. We want to measure traffic between the current server and the machine 10.11.1.227 in our local network:

~# iptables -A TARGET -d 10.11.1.227
~# iptables -A TARGET -s 10.11.1.227
~# iptables -L
Chain INPUT (policy ACCEPT)
target     prot opt source               destination         

Chain FORWARD (policy ACCEPT)
target     prot opt source               destination         

Chain OUTPUT (policy ACCEPT)
target     prot opt source               destination         

Chain TARGET (0 references)
target     prot opt source               destination         
           all  --  anywhere             10.11.1.227         
           all  --  10.11.1.227          anywhere

Next, we attach the new chain to input and output chains:

~# iptables -A INPUT -j TARGET
~# iptables -A OUTPUT -j TARGET
~# iptables -L
Chain INPUT (policy ACCEPT)
target     prot opt source               destination         
TARGET     all  --  anywhere             anywhere            

Chain FORWARD (policy ACCEPT)
target     prot opt source               destination         

Chain OUTPUT (policy ACCEPT)
target     prot opt source               destination         
TARGET     all  --  anywhere             anywhere            

Chain TARGET (2 references)
target     prot opt source               destination         
           all  --  anywhere             10.11.1.227         
           all  --  10.11.1.227          anywhere

Now everything is in place. We can finally zero the packet and byte counters, trigger a command to produce traffic and verify that the traffic was counted:

~# iptables -Z
~# nmap -nA 10.11.1.227
..snip..
~# iptables -L TARGET -n -v -x
Chain TARGET (2 references)
    pkts      bytes target     prot opt in     out     source               destination         
    4663   353156            all  --  *      *       0.0.0.0/0            10.11.1.227         
    3061   214887            all  --  *      *       10.11.1.227          0.0.0.0/0

We clearly see how many packets and bytes were transferred between the current server and 10.11.1.227.

NOTE: Using nmap for port scanning is illegal in most countries. Use it only on networks that you own or for which you have explicit scanning permissions from the owner.

After we are done we can cleanup:

~# iptables -L
Chain INPUT (policy ACCEPT)
target     prot opt source               destination         
TARGET     all  --  anywhere             anywhere            

Chain FORWARD (policy ACCEPT)
target     prot opt source               destination         

Chain OUTPUT (policy ACCEPT)
target     prot opt source               destination         
TARGET     all  --  anywhere             anywhere            

Chain TARGET (2 references)
target     prot opt source               destination         
           all  --  anywhere             10.11.1.227         
           all  --  10.11.1.227          anywhere            
~# iptables -D INPUT 1
~# iptables -D OUTPUT 1
~# iptables -F TARGET 
~# iptables -X TARGET 
~# iptables -L
Chain INPUT (policy ACCEPT)
target     prot opt source               destination         

Chain FORWARD (policy ACCEPT)
target     prot opt source               destination         

Chain OUTPUT (policy ACCEPT)
target     prot opt source               destination

Finally, here is a short script for setting up the chains and rules to measure traffic between 2 hosts:

measureTraffic.sh