Sécuriser un serveur avec fail2ban

Fail2ban est un IPS (Intrusion Prevention System) permettant de bloquer l'attaquant en se basant sur les logs du service attaqué.
En cas de detection d'attaque fail2ban créer une "jail" et bloque l'IP de l'attaquant via iptable.

Le principe est simple :

  • Créer une règle de jail (contenant le fichier de log à surveiller, le maximum de tentative, le temps de bannissement, ...)  dans /etc/fail2ban/jail.d/
  • Créer une règle de filtre (contenant la regex à appliquer pour détecter l'attaque) dans /etc/fail2ban/filter.d/

Par défaut le fichier /etc/fail2ban/jail.conf est rempli de règles non activé (directive "enabled = true" absente) je vous suggère de ne pas toucher à ce fichier et de bien créer les règles à part  dans /etc/fail2ban/jail.d (comme il est dit dans la doc)

Il est vivement déconseillé de modifier les fichiers de configuration /etc/fail2ban/fail2ban.conf et /etc/fail2ban/jail.conf (notamment car ils peuvent être écrasés par une mise à jour). Ces fichiers contiennent les configurations de base qu'on peut surcharger au moyen d'un ou plusieurs fichiers enregistrés dans /etc/fail2ban/jail.dLe fichier /etc/fail2ban/jail.conf  doit servir uniquement de référence et de documentation.

Par défaut la règles de login ssh est configuré dans /etc/fail2ban/jail.conf sur le port 22 et activé dans le fichier /etc/fail2ban/jail.d/defaults-debian.conf si le ssh est configuré sur un autre port ajoutez la ligne suivante dans /etc/fail2ban/jail.d/defaults-debian.conf

port = 22221  #adapter selon le port

Notez qu'il est possible d'ajouter une IP / nom de domaine / nom d'hôte à ignorer en cas d'erreur

#dans /etc/fail2ban/jail.conf modifier la ligne ignoreip = 127.0.0.1/8

en

ignoreip = 127.0.0.1/8 k-lfa.info 192.168.1.10  # adaptez selon vos besoins

Les premières règles à mettre en place sont celles de l'authentification des services (web, ftp, ...)  

Exemple de règle d'authentification web (pour wordpress)

#créer le fichier /etc/fail2ban/jail.d/wordpress-auth.conf

[wordpress-auth]
enabled = true
maxretry = 5
findtime = 600
bantime = 18000
filter = wordpress-auth
port = 80,443
logpath = /var/log/apache2/access.log
  • bantime : temps de banissement (10h = 36000 secondes)
  • maxretry : nombre de tentative de connexion (maximum 5 avant le ban)
  • findtime : temps avant d'oublier les tentatives de connexion ( 10 minutes = 600 secondes)
#créer le fichier /etc/fail2ban/filter.d/wordpress-auth.conf

[Definition]
failregex = ^<HOST> - .*"(POST|PUT|GET).*404.*/admin/

failregex : expression regulière qui permettera de detecter une  attaque ( surveille les requêtes en POST PUT ou GET qui provoque une  erreur 404 sur l'URL /admin/)

Exemple de règle d'authentification web (pour ghost)

#créer le fichier /etc/fail2ban/jail.d/ghost-auth.conf

[ghost-auth]
enabled = true
maxretry = 5
findtime = 600
bantime = 18000
filter = ghost-auth
port = 80,443
logpath = /var/log/apache2/access.log
  • bantime : temps de banissement (10h = 36000 secondes)
  • maxretry : nombre de tentative de connexion (maximum 5 avant le ban)
  • findtime : temps avant d'oublier les tentatives de connexion ( 10 minutes = 600 secondes)
#créer le fichier /etc/fail2ban/filter.d/ghost-auth.conf
#adaptez le champ votresite

[Definition]
failregex = ^<HOST> - .*"(POST|GET|PUT).*404.*https://votresite/ghost/.*
            ^<HOST> - .*"(POST|GET|PUT).*429.*https://votresite/ghost/.*
            ^<HOST> - .*"(POST|GET|PUT).*301.*https://votresite/ghost/.*
            ^<HOST> - .*"(POST|GET|PUT).*422.*https://votresite/ghost/.*

failregex : expression regulière qui permettera de detecter une attaque ( surveille les requêtes en POST PUT ou GET qui provoque une erreur 404/301/429/422 sur l'URL https://votresite/ghost/)

Exemple de règle antiflood web

Celui la pourra vous protéger des attaques Ddos et éventuellement des bots scan mais pourra également paralyser votre serveur si mal configuré (il est à adapté selon la fréquence de consultation)

#créer le fichier /etc/fail2ban/jail.d/http-flood.conf

[http-flood]
enabled = true
filter = http-flood
logpath = /var/log/apache2/access.log
findtime = 1000
bantime = 1200
maxretry = 10
port = http,https

alerte si 1000 requêtes en moins de 2m30 (150 secondes)

#créer le fichier /etc/fail2ban/filter.d/http-flood.conf

[Definition]
failregex = ^<HOST> - .*

la regex est simple, elle analyse toute les requêtes web (peut importe le type, la réponse HTTP ou l'URL)

Exemple de règle botscan web

Cette règle peut-être utile pour bannir les bot scannant et énumérant les directory de votre serveur web (Attention celui-ci est délicat il peut bannir très facilement ou utiliser de la ressource)

#Créer le fichier /etc/fail2ban/jail.d/botscan-http.conf

[botscan-http]

enabled=true
filter = botscan-http
logpath = /var/log/nginx/access.log #adaptez si apache
findtime = 120
bantime = 1800
maxretry = 2
port = http,https

Si 2 occurrences en 2 minutes ( plus le findtime est court plus le service consommera de puissance)

#Créer le fichier /etc/fail2ban/filter.d/botscan-http.conf

[Definition]
failregex = ^<HOST> - .* /phpmyadmin
            ^<HOST> - .* /phpMyadmin
            ^<HOST> - .* /PhpMyAdmin
            ^<HOST> - .* /phpmyAdmin
            ^<HOST> - .* /mysql
            ^<HOST> - .* /admin
            ^<HOST> - .* /server-status
            ^<HOST> - .* /cmd.php
            ...

Fichier à adaptez selon votre configuration, dans l'exemple ces dossiers n'existent pas et sont généralement scannés

Exemple de règle contre l'énumération URL

Règle utile contre les bot ou l’énumération d'URL (Cette règle peut être dangereuse si mal configurée, veillez à bien l'adaptez selon votre configuration)

#Créer le fichier /etc/fail2ban/jail.d/bot-enum.conf

[bot-enum]
enabled=true
filter = bot-enum
logpath = /var/log/nginx/access.log
findtime = 300
bantime = 7200
maxretry = 10
port = http,https

Dans ma configuration, les erreurs 301 ou 404 sont uniquement liées à une URL non existante (qui pourrait être généré en cas d’énumération)

#Créer le fichier /etc/fail2ban/filter.d/bot-enum.conf

[Definition]
failregex = ^<HOST> - .*(301|404) .*

Au bout de 10 erreurs 301 ou 404 en 5 minutes, l'IP sera bloqué 2 heures

Exemple de règle login ftp

Des règles prédéfinis existent déjà pour les services ftp classique (vsftp, proftp, ...)

#créer  le fichier /etc/fail2ban/jail.d/ftp-auth.conf

[proftpd]   #adapter avec le nom du service (proftpd dans l'exemple)
enabled = true
maxretry = 5
findtime = 600
bantime = 7200

N'oubliez pas de redémarrer le service à chaque modification

systemctl restart fail2ban

Fail2ban embarque des commandes d'administration pour créer des règles, filtre, action et pour vérifier l'état des jails

# afficher les jails actives
fail2ban-client status

#verifier l'état d'une jail (IP bannies, nombres de tentatives, ...)
fail2ban-client status sshd

#Débannir une IP
fail2ban-client set nomdelajail unbanip addressIP

#Afficher les ban via iptables 
iptable -L

Chain f2b-http-flood (1 references)
target     prot opt source               destination         
RETURN     all  --  anywhere             anywhere            

Chain f2b-sshd (1 references)
target     prot opt source               destination         
RETURN     all  --  anywhere             anywhere