Mod evasive

De Wiki Amis SH
Aller à la navigation Aller à la recherche



Le wiki : Accueil - Administrateur - Bureautique - Développeur - Intégrateur - Marketing - Multimédia - Objets numériques - Jeux - We make Hack


Présentation de mod_evasive

Le module mod_evasive pour Apache2 permet de contrer des attaques de déni de service (DoS : Denial of Service), DDOS et Brute force.
Ce module va chercher a détecter les demandes trop importantes qui sollicitent une page sur un site web en un délai de temps très court.
Utiliser mod_evasive n'est pas suffisant pour une bonne sécurité, le travail de détection et de filtrage doit s'effectuer à un niveau beaucoup plus proche de la couche réseau, voire, à un niveau matériel.
La détection d'attaques et le filtrage sur adresse IP n'est pas le travail normal d'un serveur Web comme Apache.
Ce module facile à utiliser pourra tout de même vous aider a améliorer la sécurité de votre serveur.
Il conviendra d'utiliser mod_evasive conjointement à d'autres outils complémentaires comme mod_security et Fail2Ban.
L'adresse IP de l'attaquant pourra être bloquée sur la durée avec Fail2Ban.
Si une attaque est lourde et persistante, il faudra peut-être envisager une solution d’atténuation des attaques DDoS basée sur le matériel.
Sans un pare-feu et une bonne infrastructure, une attaque DDoS lourde risque de mettre vos services hors ligne.

Installer mod_evasive

# Vérifier l'ensemble des modules présents :
sudo apache2ctl -M
sudo apache2ctl -M | grep evasive
# Installer mod_evasive :
sudo apt-get install libapache2-mod-evasive
# Afficher la liste des modules activés.
sudo ls /etc/apache2/mods-enabled/
Les fichiers evasive.conf et evasive.load ont été ajoutés.
Le fichier /etc/apache2/mods-available/mod-evasive.conf contient les directives de configuration du module.
Le fichier /etc/apache2/mods-available/mod-evasive.load indique à Apache2 où trouver le module dans le système de fichiers.
# Le module mod-evasive se charge tout seul, et, ne devrait pas avoir besoin d'être chargé avec la commande "sudo a2enmod evasive".
# Module evasive already enabled
# Créer le dossier qui va stocker les logs :
sudo mkdir /var/log/apache2/mod_evasive
sudo touch /var/log/apache2/mod_evasive/dos_evasive.log
sudo chown -R www-data:www-data /var/log/apache2/

Configurer mod_evasive

# Configurer mod_evasive :
sudo nano /etc/apache2/mods-enabled/evasive.conf
# Les directives présentes dans le fichier /etc/apache2/mods-enabled/evasive.conf seront appliquées à tous les sites gérés par Apache.
# Pour utiliser mod_evasive avec un site en particulier, ajouter les directives de mod_evasive dans le fichier de configuration du site.
# Configurer le site /etc/apache2/sites-available/mon-site.conf avec les balises <IfModule mod_evasive20.c> et <IfModule>.
# Les directives contenues dans ce fichier remplaceront alors celles de la configuration globale.
<IfModule mod_evasive20.c>
 DOSHashTableSize 3097

 # Pas plus de 2 pages par seconde.
 DOSPageCount 2
 DOSPageInterval 1

 # Pas plus de 100 requetes par seconde (Images, CSS, ...)
 DOSSiteCount 100
 DOSSiteInterval 1

 # Période en seconde durant laquelle on bloque le client.
 DOSBlockingPeriod 500

 # Ajouter une ou plusieurs adresse IP en liste blanche.
 # L'adresse IP locale peut être mise en liste blanche.
 # DOSWhitelist 127.0.0.1
 # L'adresse IP du serveur peut être mise en liste blanche.
 # DOSWhitelist 139.99.173.195
 # Les 3 adresses IP sont celles du Bot de Google.
 DOSWhitelist 66.249.65.*
 DOSWhitelist 66.249.66.*
 DOSWhitelist 66.249.71.*

 # Notifier l'alerte avec un mail.
 DOSEmailNotify admin@example.org

 # Chemin vers le dossier de log de Apache2, mod_evasive.
 # Le fichier contiendra les adresses IP blacklistées.
 # DOSLogDir "/var/log/apache2/mod_evasive"
 # Retourne un fichier par adresse IP. La valeur contenue est incohérente.
 # cat dos-127.0.0.1 qui contient 19915. 
 # Il est 19h oui, mais, 41 minutes et pas 16minutes ...
 # Prévilégier alors la gestion des logs avec sont propre script.

 # Lancer une commande avec DOSSystemCommand.
 # Lancer par exemple un script Iptables :
 # DOSSystemCommand "sudo iptables -A INPUT -s %s -j DROP"
 # Écrire les logs :
 DOSSystemCommand "/bin/echo %s >> /var/log/apache2/mod_evasive/dos_evasive.log && /bin/date >> /var/log/apache2/mod_evasive/dos_evasive.log"
</IfModule>
# Vérifier la syntaxe de la configuration de Apache2 :
sudo apache2ctl -t
# Syntax OK
# Redémarrer Apache2 pour prendre en compte les modifications :
sudo /etc/init.d/apache2 restart

Liste des paramètres

# Taille de la table de hachage. Laisser la valeur par défaut.
# Augmenter ce nombre améliore les performances mais consomme d'avantage de mémoire.
DOSHashTableSize
# Nombre de requête pour une même page dans l’intervalle DOSPageInvernal, au delà, l'adresse IP est bloquée.
DOSPageCount
# Nombre de requête pour un même site dans l’intervalle DOSPageInvernal, au delà, l'adresse IP est bloquée.
DOSSiteCount
# Nombre de requête pour une même page en secondes.
DOSPageInterval
# Nombre de requête pour un même site en secondes.
DOSSiteInterval
# Période en seconde pendant laquelle l'adresse IP sera bloquée (Un code erreur HTTP 403 Forbidden est alors retourné).
DOSBlockingPeriod
# Permet de mettre des adresses IP en liste blanche.
# DOSWhitelist 192.168.0.* autorise les requêtes provenant des machine d'un réseau local privé.
DOSWhitelist
# Notifier l'alerte avec un mail.
### Remarque sur DOSEmailNotify :
# Il est nécessaire de disposer d’un serveur de messagerie installé et fonctionnel pour que les notifications par courrier électronique puissent fonctionner.
### Aucun mail n'est envoyé lors du test avec le script perl. Pas testé d'avantage. Non fonctionnel pour le moment. ###
# mod_evasive utilise /bin/mail pour envoyer les alertes par courrier électronique.
# Créer un lien symbolique de /usr/sbin/mail vers /bin/mail : ln -s /usr/bin/mail /bin/mail
# On devrait alors pouvoir consulter les mails avec la commande "tail -f /var/mail/www-data".
# Un mail sera envoyé à chaque blocage d'adresse IP : mod_evasive HTTP Blacklisted 127.0.0.1
DOSEmailNotify admin@example.org
# Chemin vers le dossier de log de Apache2, mod_evasive.
# Retourne un fichier par adresse IP. La valeur contenue est incohérente.
# cat dos-127.0.0.1 qui contient 19915.
# Il est 19h oui, mais, 41 minutes et pas 16minutes ...
# Privilégier alors la gestion des logs avec sont propre script qui pourra être lancé avec DOSSystemCommand.
# ModEvasive se connecte également à syslog lorsque l'adresse IP est bloquée. Vous pouvez vérifier le fichier journal en utilisant : sudo cat /var/log/messages
# Le message suivant devrait s'afficher : mod_evasive[2732]: Blacklisting address 127.0.0.1: possible DoS attack.
DOSLogDir "/var/log/apache2/mod_evasive/"
# Lancer une commande avec DOSSystemCommand, par exemple, un script Iptables : DOSSystemCommand "sudo iptables -A INPUT -s %s -j DROP"
# Pour que le ban avec Iptables et mod-evasive fonctionne, il faut que www-data ait le droit de modifier Iptables, or, cela peut s'avérer très dangereux ! Il est conseillé de se servir de Fail2ban.
# Écrire ses propres logs pour mod_evasive plutôt que d'utiliser la commande de log intégrée dans mod_evasive :
# DOSSystemCommand "/bin/echo %s >> /var/log/apache2/mod_evasive/dos_evasive.log && /bin/date >> /var/log/apache2/mod_evasive/dos_evasive.log"
# Pour permettre l'écriture dans le dossier mod_evasive/ il faut changer le propriétaire et le groupe du dossier apache2 et mod_evasive/ pour www-data avec chown.
DOSSystemCommand

Tester mod_evasive

Pour tester le module, on peut changer la configuration avec des valeurs faibles pour regarder ce qui se passe.
Normalement, le dossier de log /var/log/apache2/mod_evasive/doc_evasive.log devrait se remplir d'adresses IP blacklistées. 

Résultats attendus avec le script test.pl proposé dans l'installation de mod_evasive

Utiliser le script perl "test.pl" situé dans le répertoire /usr/share/doc/libapache2-mod-evasive/examples/.
Configurer ce fichier "test.pl" avec l'adresse IP locale 127.0.0.1 puis avec l'adresse IP de votre serveur distant.
sudo nano /usr/share/doc/libapache2-mod-evasive/examples/test.pl
#!/usr/bin/perl
# test.pl: small script to test mod_dosevasive's effectiveness

use IO::Socket;
use strict;

for(0..100) {
 my($response);
 my($SOCKET) = new IO::Socket::INET( Proto   => "tcp",
                                     PeerAddr=> "127.0.0.1:80");
 if (! defined $SOCKET) { die $!; }
  print $SOCKET "GET /?$_ HTTP/1.0\n\n";
 $response = <$SOCKET>;
 print $response;
 close($SOCKET);
}
Lancer le script depuis le terminal.
sudo perl /usr/share/doc/libapache2-mod-evasive/examples/test.pl
Le script effectue 100 demandes sur votre serveur Web.
Le code de réponse 403 indique que l'accès est refusé par le serveur Web.

Résultats affichés lors du lancement de test.pl proposé par défaut

# Test effectué sur une machine virtuelle de Debian Stretch avec une installation minimaliste, par défaut, en local.
perl /usr/share/doc/libapache2-mod-evasive/examples/test.pl
HTTP/1.1 400 Bad Request
HTTP/1.1 400 Bad Request
...
# Test effectué sur un serveur VPS Debian SID.
perl /usr/share/doc/libapache2-mod-evasive/examples/test.pl
HTTP/1.1 400 Bad Request
HTTP/1.1 400 Bad Request
...
# L'erreur 400 semble signifier que la mod_evasive ne fonctionne pas, et/ou, que le script de test.pl ne fonctionne pas.
# Cela pourrait peut être également signifier que les VirtualHosts sont mal paramétrés.

Adapter le script test.pl

# Remplacer une ligne dans le fichier test.pl comme proposé depuis différents salons de discussions.
nano /usr/share/doc/libapache2-mod-evasive/examples/test.pl
# Remplacer la ligne print $SOCKET "GET /?$_ HTTP/1.0\n\n";
# Par cette nouvelle ligne print $SOCKET "GET /?$_ HTTP/1.0\r\nHost: 127.0.0.1\r\n\r\n";
### Voir si changer HTTP 1.0 pour HTTP 1.1 change le code erreur retournée.
### Forcer le protocole HTTP 1.1 pour Apache2 : https://stackoverflow.com/questions/44282207/how-to-disable-http-1-0-protocol-in-apache

Depuis la machine virtuelle de Debian Stretch

J'obtiens bien une répétition de :
HTTP/1.1 200 OK
# Le script de test semble donc bien fonctionner en local, avec une configuration minimaliste, par défaut, en local.
# L'adresse 127.0.0.1 est en liste blanche dans la configuration proposée pour la mod_evasive.
# Il y a donc répétition de la ligne HTTP/1.1 200 OK, ni plus, ni moins.
# Ne pas mettre l'adresse 127.0.0.1 en liste blanche, commenter # DOSWhitelist 127.0.0.1 depuis le fichier de configuration.
nano /etc/apache2/mods-enabled/evasive.conf
# Redémarrer Apache2 pour prendre en compte les modifications :
sudo /etc/init.d/apache2 restart
# Toujours depuis la machine virtuelle de Debian Stretch j'obtiens bien une répétition de :
# J'obtiens alors rapidement une erreur 403 en relançant le script test.pl, c'est donc que mod_evasive fonctionne.
HTTP/1.1 200 OK
HTTP/1.1 200 OK
...
HTTP/1.1 403 Forbidden
HTTP/1.1 403 Forbidden
HTTP/1.1 200 OK
HTTP/1.1 403 Forbidden
HTTP/1.1 403 Forbidden
...

Depuis le serveur VPS

# Après avoir modifié le script test.pl de la façon suivante :
#!/usr/bin/perl
# test.pl: small script to test mod_dosevasive's effectiveness

use IO::Socket;
use strict;

for(0..100) {
 my($response);
 my($SOCKET) = new IO::Socket::INET( Proto   => "tcp",
                                     PeerAddr=> "139.99.173.195:80");
 if (! defined $SOCKET) { die $!; }
 #  print $SOCKET "GET /?$_ HTTP/1.0\n\n";
 print $SOCKET "GET /?$_ HTTP/1.0\r\nHost: 139.99.173.195:80\r\n\r\n";
 $response = <$SOCKET>;
 print $response;
 close($SOCKET);
}
# Quand je met 127.0.0.1 dans la liste blanche depuis le fichier de configuration, j'obtiens l'erreur 400.
HTTP/1.1 400 Bad Request
HTTP/1.1 400 Bad Request
...
# Quand je ne met pas 127.0.0.1 dans la liste blanche depuis le fichier de configuration, j'obtiens l'erreur 503 puis l'erreur 403 attendue.
# Je ne comprend pas pourquoi le code 503 est retourné sur mon test en production, mais, le passage au code 403 semble signifier que mod_evasive fonctionne.
HTTP/1.1 503 Service Unavailable
HTTP/1.1 503 Service Unavailable
...
HTTP/1.1 403 Forbidden
HTTP/1.1 403 Forbidden
...

Tester mod_evasive avec Apache bench

Utiliser Apache bench (ab) - Apache HTTP outil d'analyse comparative des serveurs (Apache bench (ab) - Apache HTTP server benchmarking tool).
Source : http://httpd.apache.org/docs/2.2/programs/ab.html
# Lancer la commande suivante pour démarrer un test en local et la même commande pour un test en production.
ab -n152 -c152 127.0.0.1/index.php
# Je met la valeur 150 pour les variables -n et -c afin d'être sur de dépasser la limite fixée de 150, dans la configuration de mod_evasive.
# -n : Nombre de demandes à exécuter pour la session d'analyse comparative.
# -c : Nombre de requêtes multiples à exécuter à la fois.
######################################################################################################
# Suite au test en production, j'ai remplacé l'adresse IP 127.0.0.1 par celle du serveur 139.99.173.195.
# Je me retrouve avec le site innaccessible avec une page blanche et "error".
# Je consulte les logs et je vois que mon IP de la box apparait de nombreuses fois lors du Deni de service, ce qui est normal.
# Je me dis que surement elle a été ajoutée à Iptables. Je tente de la retirer avec la mauvaise commande "iptables -R INPUT 1 -s xx.xx.xxx.xx -j DROP", et, je me retrouve bloqué.
# Le site lui, reste en page blanche, et affiche "error".
######################################################################################################
# Objectif 1 : Redémarrer le serveur.
# -> Cette étape aura suffit pour me reconnecter au serveur.
# -> DemocracyOS n'est plus disponible. Il faut le redémarrer.
# Objectif 2 : Changer d'adresse IP avec un VPN pour me reconnecter au serveur.
# Objectif 3 : Vérifier Iptables et retirer l'adresse IP de la box.
# Objectif 4 : Vérifier l'accès au serveur.
# Objectif 5 : Nettoyer les logs.
######################################################################################################
This is ApacheBench, Version 2.3 Revision: 1757674 
Copyright 1996 Adam Twiss, Zeus Technology Ltd.
Licensed to The Apache Software Foundation, http://www.apache.org/

Benchmarking 127.0.0.1 (be patient)
Completed 100 requests
Finished 152 requests

Server Software:        Apache/2.4.25
Server Hostname:        127.0.0.1
Server Port:            80

Document Path:          /index.php
Document Length:        293 bytes

Concurrency Level:      152
Time taken for tests:   0.289 seconds
Complete requests:      152
Failed requests:        6
  (Connect: 0, Receive: 0, Length: 6, Exceptions: 0)
Non-2xx responses:      146
Total transferred:      213946 bytes
HTML transferred:       185002 bytes
Requests per second:    525.74 [#/sec] (mean)
Time per request:       289.119 [ms] (mean)
Time per request:       1.902 [ms] (mean, across all concurrent requests)
Transfer rate:          722.65 [Kbytes/sec] received

Connection Times (ms)
             min  mean[+/-sd] median   max
Connect:        2    7  12.4      2      41
Processing:    13   96  62.5     80     282
Waiting:       13   95  60.7     80     269
Total:         42  103  58.7     83     287

Percentage of the requests served within a certain time (ms)
 50%     83
 66%    104
 75%    118
 80%    118
 90%    212
 95%    213
 98%    286
 99%    287
100%    287 (longest request)
# Une fois le test terminé, consulter les logs de mod_evasive.
# Un fichier aura été créé, ou, l'adresse IP aura été ajoutée dans le fichier existant.
# On peut en conclure que mod_evasive fonctionne correctement avec un test d'attaque DOS fait en local.
/var/log/apache2/mod_evasive# ls
dos_evasive.log
/var/log/apache2/mod_evasive# cat dos_evasive.log 
127.0.0.1
Thu Nov  8 20:56:21 CET 2018

Tester mod_evasive avec un script JavaScript

# Rendre le fichier dos.php disponible depuis : https://www.domaine.fr/dos.php
<?php
header("Access-Control-Allow-Origin: *");
echo "ok";
# Lancer une attaque depuis https://js.do avec le script suivante :
<script>
setInterval(function(){
   var xhr = new XMLHttpRequest();
   xhr.open("GET", 'https://www.domaine.fr/dos.php');
   xhr.onreadystatechange = function() {
       if (xhr.readyState == 4 && xhr.status == 200) {
       }
   };
	xhr.onerror = function () {
       console.log('error');
   };
   xhr.send();
});
</script>
# Ou encore ce script simplifié :
<script>
setInterval(function(){  
   var xhr = new XMLHttpRequest(); 
   xhr.open("GET", 'https://www.domaine.fr/dos.php');  
   xhr.send();
},1);
</script>

Tester mod_evasive avec LOIC pour Windows

LOIC est un programme de Stress Test Réseau fonctionnant sous Windows.
Télécharger la version Low Orbit Ion Cannon | When harpoons, air strikes and nukes fails | v. 1.0.8.0 depuis Sourceforge : https://sourceforge.net/projects/loic/files/latest/download
Une version plus transparente et récente est proposée depuis Github : https://github.com/NewEraCracker/LOIC
Pour générer une charge de travail, suivre l'ordre indiqué dans la capture d'écran ci-dessous et ne toucher à rien d'autre :

Purger le fichier de blacklist

La crontab suivante permet de purger le fichier de blacklist de temps en temps :
# Vider le fichier mod_evasive
00 5 * * * find /var/log/apache2/mod_evasive -mtime +1 -type f -exec rm -f '{}' \;

Avis complémentaires

Réglages Apache2 pour mod_evasive

Les réglages suggérés pour Apache doivent avoir une valeur très élevée pour MaxRequestsPerChild mais pas un nombre illimité (une valeur égale à zéro implique un nombre illimité).
Laisser KeepAlive activé avec KeepAliveTimeout défini pour une durée suffisamment longue.

Rôle du Pare-feu IDS IPS

Ezra-S 7 Août 17 à 18:12 Source : https://serverfault.com/questions/867101/mod-evasive-doesnt-do-anything-on-ubuntu-server-16-04
Je n’utiliserais jamais les modules httpd (tiers ou non) pour faire le travail d'un pare-feu ou d’un ids / ips.
Chaque couche a ses outils appropriés pour le travail, et, utiliser un serveur http pour bloquer les ips dynamiquement ne convient tout simplement pas.

Bibliographie

 Libapache2-mod-evasive : https://wiki.debian-fr.xyz/Libapache2-mod-evasive
 Fail2ban avec mod-evasive : https://wiki.debian-fr.xyz/Fail2ban#Fail2ban_avec_mod-evasive
 Sécurité Apache 2 : mod_evasive : https://jeanphi.net/blog/2013/06/securite-apache-2-mod_evasive
 How to harden Apache web server with mod_security and mod_evasive on CentOS : http://xmodulo.com/harden-apache-web-server-mod_security-mod_evasive-centos.html
 Apache2.4 mod_evasive 400 Bad Request : https://www.developpez.net/forums/d1910264/webmasters-developpement-web/serveurs-apache-iis/apache/apache2-4-mod_evasive-http-1-1-400-bad-request
 How To Protect Against DoS and DDoS with mod_evasive for Apache : https://www.digitalocean.com/community/tutorials/how-to-protect-against-dos-and-ddos-with-mod_evasive-for-apache-on-centos-7
 Ce contenu de recherche effectué par Visionduweb sur mod_evasive est partagé sur le wiki officiel de Debian : https://wiki.debian.org/Apache -> https://wiki.debian.org/fr/Apache/mod_evasive
 How to Protect Against DDoS with Mod_evasive on Apache Server : https://www.maketecheasier.com/mod-evasive-protect-ddos/
 Apache mod security, mod evasive : limitation du traffic, protection anti-DDOS : https://wiki.kogite.fr/index.php/Apache_mod_security,_mod_evasive_:_limitation_du_traffic,_protection_anti-DDOS
 Protect apache-using-mod_security and mod_evasive https://www.tecmint.com/protect-apache-using-mod_security-and-mod_evasive-on-rhel-centos-fedora/

NAVIGATION

PARTICIPER ET PARTAGER

Bienvenue sur le wiki de Amis SH.
De nombreuses pages sont partagées sur ce wiki.
Créer un compte utilisateur pour participer sur le wiki.
Les pages présentées sur le wiki évoluent tous les jours.
Certaines recherches sont peu abouties et incluent des erreurs.
Utiliser la recherche interne du wiki pour trouver votre contenu.
La page de discussion de Amis SH vous permet de poser vos questions.
Consulter le site amis-sh.fr pour installer votre propre serveur web.
Améliorer le contenu des pages avec vos retours depuis l'onglet discussion.
Ce contenu ne doit pas servir à nuire à autrui ou à un système informatique.
Protéger votre système Linux ou Windows avec cette page dédiée à la sécurité.

SOUTENIR CE WIKI

Soutenir le wiki avec un don en monnaie numérique :
AEON - Bitcoins - Bitcoins Cash - Bitcoins Gold - Bitcore - Blackcoins - Basic Attention Token - Bytecoins - Clams - Dash - Monero - Dogecoins - Ğ1 - Ethereum - Ethereum Classique - Litecoins - Potcoins - Solarcoins - Zcash

OBTENIR DE LA MONNAIE NUMERIQUE

Obtenir gratuitement de la monnaie numérique :
Miner de la cryptomonnaie.