Shell-Skript zum Sperren einer IP

8

Einige der IPs öffnen Tausende von Verbindungen meines Servers. Ich habe einen Ubuntu 14-Server. Ich überprüfe die Gesamtzahl der Verbindungen mit folgendem Befehl:

netstat -an | grep tcp | awk '{print $ 5}' | cut -f 1 -d: | sortieren | uniq -c | sort -n

Dann verwende ich die folgende iptables-Regel, um die IP des Täters zu blockieren.

iptables -I INPUT 1 -s xxxx -j DROP

Es funktioniert alles gut und blockiert die IP-Adresse. Ich kann jedoch nicht rund um die Uhr online bleiben, um den Server zu überwachen. Ich habe mich gefragt, ob es ein Shell-Skript gibt, mit dem ich es automatisch ausführen kann. Wenn eine IP beispielsweise zu einem beliebigen Zeitpunkt mehr als X Verbindungen öffnet, sollte sie automatisch durch die oben genannte iptables-Regel gesperrt werden.

user3404047
quelle
6
Haben Sie nachgesehen, ob fail2ban Ihren Anforderungen entspricht?
John1024
Entschuldigen Sie mein begrenztes Wissen. Ist fail2ban nicht für die SSH-Authentifizierung? Ich bin nicht sicher, ob ich es an Port 80 verwenden soll. Außerdem ist mein Server ein Chat-Server, sodass ein Benutzer mehrmals versuchen kann, eine Verbindung herzustellen / zu pingen. In diesem Fall würde fail2ban viele falsch-positive Alarme erzeugen und legitimen Datenverkehr verbieten. Jeder Gedanke?
user3404047

Antworten:

10

Erfinden Sie das Rad zunächst nicht neu. Genau dafür denyhostsist gedacht:

   DenyHosts  is a python program that automatically blocks ssh attacks by
   adding entries to /etc/hosts.deny.  DenyHosts will  also  inform  Linux
   administrators  about  offending  hosts,  attacked users and suspicious
   logins.

Soweit ich weiß, denyhostsist nur für sshVerbindungen, aber es gibt auch so fail2banziemlich alles:

   Fail2Ban consists of a client, server and configuration files to  limit
   brute force authentication attempts.

   The  server  program  fail2ban-server is responsible for monitoring log
   files and issuing ban/unban commands.  It  gets  configured  through  a
   simple  protocol  by fail2ban-client, which can also read configuration
   files and issue corresponding configuration commands to the server.

Beide sind in den Repositories verfügbar:

sudo apt-get install denyhosts fail2ban

Sie können dies auch skripten, wenn Sie möchten. Etwas wie:

#!/usr/bin/env sh
netstat -an | 
    awk -vmax=100 '/tcp/{split($5,a,":"); if(a[1] > 0 && a[1]!="0.0.0.0"){c[a[1]]++}}
    END{for(ip in c){if(c[ip]>max){print ip}}}' |
        while read ip; do iptables -I INPUT 1 -s "$ip" -j DROP; done

Das awkextrahiert die IPs und zählt sie und druckt nur diejenigen, die öfter erscheinen als maxhier (hier -vmax=100ändern Sie sie entsprechend). Die IPs werden dann einer while-Schleife zugeführt, in der die entsprechende iptablesRegel ausgeführt wird.

Um dies rund um die Uhr auszuführen, würde ich einen Cronjob ausführen, der den Befehl über jede Minute oder so ausführt. Fügen Sie diese Zeile hinzu/etc/crontab

* * * * * root /path/to/script.sh
Terdon
quelle
Danke terdon für eine genaue Antwort. AFAIK, fail2ban dient zur SSH-Authentifizierung. Alle Verbindungen werden auf Port 80 geöffnet. Ich werde untersuchen, ob ich fail2ban auf Port 80 verwenden kann. Wie kann ich das benutzerdefinierte Skript rund um die Uhr im Hintergrund ausführen? Bildschirmbefehl? Oder cron installieren? Übrigens. Ich verwende den Server als Chat-Server, damit eine Person viele Male pingen (oder mehrere Verbindungen öffnen) kann, damit ich das von Ihnen bereitgestellte benutzerdefinierte Skript verwenden kann.
user3404047
2
@ user3404047 Sie könnten es als Cronjob ausführen, ja. Siehe aktualisierte Antwort. Ist fail2banaber nicht nur für ssh. Es funktioniert auch gut für Port 80. Siehe zum Beispiel hier , hier und hier .
Terdon
1

Eine mögliche alternative Option besteht darin, die problematischen IP-Adressen innerhalb des iptables-Regelsatzes mithilfe des recentModuls zu identifizieren und zu behandeln . Die Herausforderung bei dieser Methode ist das Standard-Hitcount-Limit von 20, daher muss man entweder von den Standardeinstellungen abweichen oder übergeordnete Carry-Zähler erstellen, um einen höheren Hitcount-Triggerpunkt zu erreichen.

Das folgende Beispiel stammt aus meinem iptables-Regelsatz und sperrt eine IP-Adresse für etwas mehr als 1 Tag, wenn in weniger als 12 Minuten 80 neue TCP-Verbindungen auf Port 80 hergestellt werden. Sobald Sie sich auf der Liste der Bösewichte befinden, wird bei jedem Verbindungsversuch der 1-Tages-Zähler auf 0 zurückgesetzt. Diese Methode kann maximal 400 Treffer erreichen, bevor eine Erweiterung auf einen anderen Übertrag erforderlich ist (und ich habe eine andere Übertragskette getestet). Beachten Sie, dass der veröffentlichte Code über die Infrastruktur verfügt, mit der nur mehrere kürzere Zeitauslöser für eine lange Zeit gesperrt werden können. Derzeit habe ich es so eingestellt, dass es beim ersten Auslöser nur für eine lange Zeit gesperrt wird.

#######################################################################
# USER DEFINED CHAIN SUBROUTINES:
#
# http-new-in4
#
# A NEW Connection on port 80 part 4.
#
# multiple hits on the banned list means you get a one day ban.
# (I re-load the firewall rule set often, so going longer makes
# little sense.)
#
# Custom tables must exist before being referenced, hence the order
# of these sub-toutines.
#
# Place holder routine, but tested. Logs if a day ban would have
# been activated.
#
$IPTABLES -N http-new-in4
#$IPTABLES -A http-new-in4 -m recent --set --name HTTP_BAN_DAY

$IPTABLES -A http-new-in4 -j LOG --log-prefix "DAY80:" --log-level info
$IPTABLES -A http-new-in4 -j DROP

#######################################################################
# USER DEFINED CHAIN SUBROUTINES:
#
# http-new-in3
#
# A NEW Connection on port 80 part 3.
#
# carry forward to the actual banned list:
# Increment this count. Leave the previous count.
#
# Custom tables must exist before being referenced, hence the order
# of these sub-toutines.
#
$IPTABLES -N http-new-in3
$IPTABLES -A http-new-in3 -m recent --remove --name HTTP_02
$IPTABLES -A http-new-in3 -m recent --update --hitcount 1 --seconds 86400 --name HTTP_BAN -j http-new-in4
$IPTABLES -A http-new-in3 -m recent --set --name HTTP_BAN

$IPTABLES -A http-new-in3 -j LOG --log-prefix "BAN80:" --log-level info
$IPTABLES -A http-new-in3 -j DROP

#######################################################################
# USER DEFINED CHAIN SUBROUTINES:
#
# http-new-in2
#
# A NEW Connection on port 80 part 2.
#
# carry forward from previous max new connections per unit time:
# Increment this count and clear the lesser significant count.
#
$IPTABLES -N http-new-in2
$IPTABLES -A http-new-in2 -m recent --remove --name HTTP_01
$IPTABLES -A http-new-in2 -m recent --update --hitcount 3 --seconds 720 --name HTTP_02 -j http-new-in3
$IPTABLES -A http-new-in2 -m recent --set --name HTTP_02

$IPTABLES -A http-new-in2 -j LOG --log-prefix "CARRY80:" --log-level info
$IPTABLES -A http-new-in2 -j ACCEPT

#######################################################################
# USER DEFINED CHAIN SUBROUTINES:
#
# http-new-in
#
# A NEW Connection on port 80:
#
$IPTABLES -N http-new-in

echo Allowing EXTERNAL access to the WWW server

# . check the static blacklist.
#
# http related
$IPTABLES -A http-new-in -i $EXTIF -s 5.248.83.0/24 -j DROP
... delete a bunch on entries ...
$IPTABLES -A http-new-in -i $EXTIF -s 195.211.152.0/22 -j DROP
$IPTABLES -A http-new-in -i $EXTIF -s 198.27.126.38 -j DROP

# . check the dynamic banned list
#
# The 1 Hour banned list (bumped to more than a day):
$IPTABLES -A http-new-in -m recent --update --seconds 90000 --name HTTP_BAN --rsource -j LOG --log-prefix "LIM80:" --log-level info
$IPTABLES -A http-new-in -m recent --update --seconds 90000 --name HTTP_BAN --rsource -j DROP

# A generic log entry. Usually only during degugging
#
#$IPTABLES -A http-new-in -j LOG --log-prefix "NEW80ALL:" --log-level info

# Dynamic Badguy List. Least significant hit counter.  Detect and DROP Bad IPs that do excessive connections to port 80.
#
$IPTABLES -A http-new-in -m recent --update --hitcount 20 --seconds 240 --name HTTP_01 -j http-new-in2
$IPTABLES -A http-new-in -m recent --set --name HTTP_01

$IPTABLES -A http-new-in -j LOG --log-prefix "NEW80:" --log-level info
$IPTABLES -A http-new-in -j ACCEPT

... a bunch of stuff not included here

# Allow any related traffic coming back to the server in.
#
#
$IPTABLES -A INPUT -i $EXTIF -s $UNIVERSE -d $EXTIP -m state --state ESTABLISHED,RELATED -j ACCEPT

... the above is needed before the below ...

# If required, go to NEW HTTP connection sub-routine
#
$IPTABLES -A INPUT -i $EXTIF -m state --state NEW -p tcp -s $UNIVERSE -d $EXTIP --dport 80 -j http-new-in
Doug Smythies
quelle