Next Previous Contents

5. Tarpitting the scanner or worm

Blocking the scanner or worm protects our network from further attack. We'd also like to be good network citizens and make the scanner's life hard, to take some of the load off other admins who might be the attacker's next target.

The tool for doing this is called LaBrea. Basically it plays tricks with the TCP flow control settings to tell the scanning computer “Yes, I'm here, but I can only accept one byte per packet,” and then doesn't acknowlege packets so the sender sits in a timeout-and-retransmit loop for long periods of time. Ideally the scanner will hit the tarpit and become stuck for hours on end, trying vainly to see whether we're running a vulnerable version of IIS and leaving some other unprotected network alone.

This response is effective where the scanner is checking for version banners or other indications of a specific vulnerability, or is a worm trying to propagate itself. On scans that are only looking for running servers (e.g. “half-open” or “stealth” scans) this won't slow the scanner, but has the benefit of polluting the scanner's database of “hits” - most of the hosts on the boundary network will be reported as running the service that the scanner is looking for. Even if the host does not really exist.

LaBrea is designed to be installed as the only service running on a dedicated “tarpit host” that is sitting on the boundary network. However, the fact that we are using transparent proxy and Portsentry to detect and block scans of the boundary network means that this model won't work. Instead, we'll run LaBrea on the outer firewall itself.

5.1 Running LaBrea on the outer firewall

(NOTE: a new LaBrea is currently in beta release, and some changes are needed for it to run on a T1 vs. on a standard Ethernet interface, and to improve its behavior in the application described here. See the patch file for the needed changes. They may already be in the beta when you read this.)

LaBrea has sophisticated facilities for acting as if it were all of the nonexistent hosts on the boundary network in a dynamic manner. Since we're running it on the outer firewall, and we only want to tarpit hosts after a scan is detected, we need to turn off some of the smarts in LaBrea, and tell it explicitly which hosts we want it to tarpit. Fortunately, LaBrea supports a packet filtering mechanism via libpcap. Make sure you have a recent version of libpcap - older versions have a bug that prevents proper operation when the filter passes a certain size.

To generate the packet filter we need to capture the attacking IP addresses in a file, which the Portsentry blacklist script is doing. This file is then used to generate the packet filter file for LaBrea.


INET_IF=wp1_chdlc   # the T1 - may be eth1 for non-T1 firewalls
NETWORK=' -n -m '

# don't run this script in parallel
# this could definitely use some improvement
while [ -s $BPF.lock ]
        if ps -p `cat $BPF.lock` >/dev/null 2>&1
                # lock is valid
                if [ -s $BPF.lock.2 ]
                        # another rebuild already queued
                        echo $$ > $BPF.lock.2
                        sleep 5
                        rm -f $BPF.lock.2
                rm -f $BPF.lock $BPF.lock.2

echo $$ > $BPF.lock

if [ -s $EVIL ]
    rm -f $BPF
    echo 'tcp and src host ( ' > $BPF

    /usr/bin/perl -n -e 's/#.*//;
      if (
         ) {print "$1\n";}' $EVIL |\
    uniq | tail -200 | sort | uniq | sed -e 's|/.*||' \
    while read IP_TO_BLOCK
        echo "$IP_TO_BLOCK or " >> $BPF

    echo ' )' >> $BPF

rm -f $BPF.lock $BPF.lock.2

if ps -ef | grep -v grep | grep -q Labrea
        # re-read packet filter file
        killall -HUP LaBrea
        # start LaBrea
        exec /usr/local/sbin/LaBrea -z -i $INET_IF -l -v -j -x $NETWORK -F $BPF

To manage LaBrea automatically, we make a “respawn” entry in /etc/inittab:

# run the tarpit daemon

And in the /etc/portsentry/portsentry.blacklist script that Portsentry runs to blackhole a new scanning host, we append a command to run the tarpit script to update the packet filter:

nice /usr/local/sbin/tarpit

Next Previous Contents