Create GeoIP firewall rules for iptables
Create GeoIP firewall rules for iptables

This script creates automatically firewall rules for iptables based on GeoIP informations. This script can be useful if you cannot use or build from source the Xtables addons for iptables.

The script allows you to authorize network trafic on a specific tcp port for a/multiple countr(y/ies). It is exclusive : if a tcp port/country has been defined with this script, only this country subnet address will be able to reach the tcp port.

The script performs these steps :

  • Download the file http://geolite.maxmind.com/download/geoip/database/GeoIPCountryCSV.zip
  • Unzip the file above
  • Check if the country code is valid or not
  • Create an iptables custom chain for each Country Code-TCP port to allow
  • Create a DROP rule in the INPUT chain to drop all traffic that is not defined in the rule above

Country code reference

Script syntax :
Authorize on port TCP 999 only network subnet from XX Country code

./scriptname "XX" 999

 

Authorize on port TCP 999 only network subnet from XX, YY and ZZ Country code

./scriptname "XX|YY|ZZ" 999

 

Script :

#!/bin/bash
COUNTRY=$1
COUNTRY=$(echo $COUNTRY | tr 'a-z' 'A-Z')
TCPPORT=$2

# function to create iptables entries
ipt_create() {
        file="$1"
        pattern="$2"
        tcpport="$3"
        if cat $file | cut -f5 -d, | grep $pattern >/dev/null ; then
                echo $pattern "is valid. Creating iptables custom chain DROP_EXCEPT_"$pattern"..."
                if ! iptables -L | grep "Chain DROP_EXCEPT_"$pattern >/dev/null ; then
                        sudo iptables -N DROP_EXCEPT_$pattern'_ONPORT_'$tcpport
                fi
                if ! iptables -L INPUT | grep DROP_EXCEPT_$pattern >/dev/null ; then
                        sudo iptables -t filter -I INPUT -j DROP_EXCEPT_$pattern'_ONPORT_'$tcpport
                fi
                cat $file | grep -E $pattern | sed 's/"//g' | sort | uniq > $file.$pattern

                while IFS=, read -r ip_begin ip_end f3 f4 f5 f6
                do
                        echo "for "$f6" : sudo iptables -A DROP_EXCEPT_"$pattern" -p tcp -m tcp -m iprange --src-range "$ip_begin"-"$ip_end" --dport "$tcpport" -j ACCEPT"
                        sudo iptables -A DROP_EXCEPT_$pattern'_ONPORT_'$tcpport -p tcp -m tcp -m iprange --src-range $ip_begin-$ip_end --dport $tcpport -j ACCEPT
                done < $file.$pattern
        else
                echo $pattern "is invalid. Skipping."
        fi
}

cd /geoip
ZIP="GeoIPCountryCSV.zip"
if [ -f $ZIP ];
then
   mv -f $ZIP $ZIP.bkp
fi
/usr/bin/wget -P . http://geolite.maxmind.com/download/geoip/database/$ZIP
CSV=$(unzip -l $ZIP | grep -i "\.csv" | awk '{print $4}')
if [ -f $CSV ];
then
   mv -f $CSV $CSV.bkp
fi
unzip -o $ZIP

# create iptables chain for each country
if [[ $COUNTRY == *\|* ]]
then
        for XX in ${COUNTRY//\|/ } ; do
                if ! iptables -L | grep "Chain DROP_EXCEPT_"$XX >/dev/null ; then
                        ipt_create $CSV $XX $TCPPORT
                else
                        echo "iptables chain for "$XX" already exists. Skipping."
                fi
        done
else
        if ! iptables -L | grep "Chain DROP_EXCEPT_"$COUNTRY >/dev/null ; then
                ipt_create $CSV $COUNTRY $TCPPORT
        else
                echo "iptables chain for "$COUNTRY" already exists. Skipping."
        fi

fi

if ! iptables -L INPUT | grep "tcp dpt:"$TCPPORT >/dev/null ; then
        sudo iptables -A INPUT -p tcp -m tcp --dport $TCPPORT -j DROP
fi

Create GeoIP firewall rules for iptables

Leave a Reply

Your email address will not be published.