Linux Geo-Blocking mit IPSet, UFW und IPTables inkl. Firehol Blocklist

Hier beschreibe ich, wie man Geoblocking mit IPSet, UFW und IPTables einrichten kann. Wie immer gilt: Kein Backup, kein Mitleid!

Ich gehe davon aus, dass ein lauffähiges Ubuntu 22.04 LTS mit IPTables und UFW vorliegt. Ebenso SSH-Zugriff auf den Server sowie root Rechte.

Beachtet bitte dass ZWINGEND UFW auf eurem System funktionsfähig ist und der Status "aktiv" ist.

systemctl status ufw

IPSet installieren:

apt install ipset && mkdir /etc/ipset

Erstellen der IPv4 und IPv6 Nethashes:

Falls kein IPv6 benötigt wird, bitte weglassen!

ipset --create blocked-countries-ipv4 nethash maxelem 10000000 
ipset --create blocked-countries-ipv6 nethash maxelem 10000000 family inet6

ipset create firehol nethash maxelem 10000000
ipset --create firehol_webserver nethash maxelem 10000000
ipset --create firehol_openproxys nethash maxelem 10000000
ipset --create firehol_tor_exits nethash maxelem 10000000
ipset --create firehol_ssh nethash maxelem 10000000
ipset --create firehol_mail nethash maxelem 10000000
ipset --create firehol_imap nethash maxelem 10000000
ipset --create firehol_bruteforce nethash maxelem 10000000
ipset --create firehol_strongips nethash maxelem 10000000

Herunterladen des Scripts, dass die Country-Zonenfiles v4+v6 holt und importiert sowie Script ausfürbar machen:

cd /etc/ipset/ && wget https://github.com/AnID-Aux/IPset-Geoblock/raw/main/import-zones.sh && chmod +x import-zones.sh

only v4 wäre hier:

cd /etc/ipset/ && wget https://github.com/AnID-Aux/IPset-Geoblock/raw/main/import-zones-only-v4.sh && chmod +x import-zones-only-v4.sh

Nun die Datei ausführen um die Nethash Sets zu befüllen:

/bin/sh /etc/ipset/import-zones.sh

Das Script dauert eine Weile (bis zu 35 Minuten), je nach Anzahl der Einträge. Wenn das Script durchgelaufen ist fügen wir die neuen IPSet Nethashes in die IPTables Firewall ein: IPv6?

iptables -A INPUT -m set --match-set blocked-countries-ipv4 src -j DROP
ip6tables -A INPUT -m set --match-set blocked-countries-ipv6 src -j DROP
iptables -A INPUT -m set --match-set firehol src -j DROP
iptables -A INPUT -m set --match-set firehol_webserver src -j DROP
iptables -A INPUT -m set --match-set firehol_openproxys src -j DROP
iptables -A INPUT -m set --match-set firehol_tor_exits src -j DROP
iptables -A INPUT -m set --match-set firehol_ssh src -j DROP
iptables -A INPUT -m set --match-set firehol_mail src -j DROP
iptables -A INPUT -m set --match-set firehol_imap src -j DROP
iptables -A INPUT -m set --match-set firehol_bruteforce src -j DROP
iptables -A INPUT -m set --match-set firehol_strongips src -j DROP

Jetzt speichern wir die IP-Set Config:

ipset save > /etc/ipset/ipsets.conf

und legen uns einen SystemD Service an:

nano /etc/systemd/system/ipset-persistent.service

hier fügen wir folgendes ein:

[Unit]
Description=ipset persistency service
DefaultDependencies=no
Requires=ufw.service
Before=network.target
Before=ufw.service
ConditionFileNotEmpty=/etc/ipset/ipsets.conf

[Service]
Type=oneshot
RemainAfterExit=yes
ExecStart=/sbin/ipset -exist -file /etc/ipset/ipsets.conf restore
ExecStop=/sbin/ipset -file /etc/ipset/ipsets.conf save

[Install]
WantedBy=multi-user.target
RequiredBy=ufw.service

Nun aktivieren wir den Service:

systemctl daemon-reload && systemctl enable --now ipset-persistent.service

Damit beim neustart die Regeln wieder gesetzt werden fürgen wir folgenden Cronjob ein: IPv6?

crontab -e
@reboot sleep 30 && /sbin/iptables -A INPUT -m set --match-set blocked-countries-ipv4 src -j DROP
@reboot sleep 35 && /sbin/ip6tables -A INPUT -m set --match-set blocked-countries-ipv6 src -j DROP
@reboot sleep 41 && /sbin/iptables -A INPUT -m set --match-set firehol src -j DROP
@reboot sleep 42 && /sbin/iptables -A INPUT -m set --match-set firehol_webserver src -j DROP
@reboot sleep 43 && /sbin/iptables -A INPUT -m set --match-set firehol_openproxys src -j DROP
@reboot sleep 44 && /sbin/iptables -A INPUT -m set --match-set firehol_tor_exits src -j DROP
@reboot sleep 45 && /sbin/iptables -A INPUT -m set --match-set firehol_ssh src -j DROP
@reboot sleep 46 && /sbin/iptables -A INPUT -m set --match-set firehol_mail src -j DROP
@reboot sleep 46 && /sbin/iptables -A INPUT -m set --match-set firehol_imap src -j DROP
@reboot sleep 47 && /sbin/iptables -A INPUT -m set --match-set firehol_bruteforce src -j DROP
@reboot sleep 48 && /sbin/iptables -A INPUT -m set --match-set firehol_strongips src -j DROP

@reboot sleep 1200 && nice -n 10 /bin/bash /etc/ipset/import-zones.sh
@weekly nice -n 10 /bin/bash /etc/ipset/import-zones.sh

Tests:

ipset list -name
ipset list -terse
iptables -S
iptables -S | grep blocked-countries-ipv4
ip6tables -S | grep blocked-countries-ipv6
iptables -xvnL
service iptables status
service ufw status
service ipset status
service ipset-persitent status

Blocklists

https://www.ipdeny.com/ipblocks

https://github.com/herrbischoff/country-ip-blocks

http://iplists.firehol.org

Dateien umschreiben IPv4 / IPv6

sed -i 's#https://www.ipdeny.com/ipblocks/data/aggregated/#https://ipdeny.com/ipv6/ipaddresses/aggregated/#g' Dateiname
sed -i 's/IPv4/IPv6/g' Dateiname