A la fin de [mon article sur le blocage des attaques de brute force](/2017/securite-des-donnees-focus-sur-nextcloud), j'étais resté sur l'envoi quotidien d'un e-mail avec le log des attaques de la journée, histoire d'avoir une idée de ce qui s'est passé. Pour rappel, mon serveur tourne sous OpenBSD et l'outil de protection contre les attaques est Vilain, un équivalent de Fail2ban sous Linux. Le log de la journée est fastidieux à lire et j'ai eu envie de construire un rapport avec les informations suivantes : - liste des adresses IP bloquées - répartition horaire des attaques - top des adresses IP les plus agressives Après un échange avec [Thuban](http://yeuxdelibad.net), le créateur de Vilain, nous convenons que Vilain doit rester [KISS](https://fr.wikipedia.org/wiki/Principe_KISS), qu'il n'est pas souhaitable de compliquer son code pour générer un rapport. Il est préférable de réaliser le travail en externe en analysant les logs. C'est ainsi que j'ai écrit **vilainreport** (une centaine de lignes en Python), qu'on peut lancer quotidiennement avec une tâche CRON pour recevoir le rapport du jour : cat /var/log/vilain | vilainreport | mail -s "Vilain rapport du jour" admin **vilainreport** est intégré au [dépôt de Vilain sur Framagit](https://framagit.org/Thuban/vilain). Voici un exemple de rapport généré par *vilainreport*: ### Date 2017-10-12 00:17:00 blacklist IP 156.196.136.52 (ssh) 01:26:17 blacklist IP 115.249.139.206 (ssh) 02:31:08 blacklist IP 218.62.64.179 (ssh) 02:35:16 blacklist IP 91.223.167.69 (ssh) 02:46:54 blacklist IP 27.102.203.180 (ssh) ... Probe 'ssh' : 137 attacks ### Attacks per probe Probe 'ssh': 137 attacks ### Hourly repartition Hour 00 - 01: 1 Hour 01 - 02: 1 Hour 02 - 03: 4 Hour 03 - 04: 4 ... ### Top attackers IP 195.184.191.147 : 6 IP 81.4.110.104 : 5 IP 90.63.248.112 : 5 IP 176.31.126.176 : 5 ... Ma configuration personnelle de Vilain est la suivante : je bannis pendant 1 heure toute adresse après sa deuxième tentative erronée de connexion à un de mes services. Donc un *Top attacker* qui a été banni 6 fois dans la même journée n'a pas fait d'erreur de connexion. Il a vraiment l'intention de s'introduire dans mon serveur. Je pourrais durcir ma configuration pour bannir beaucoup plus d'une heure mais ça ne m'arrange pas car je partage des documents avec des gens qui peuvent se tromper une fois ou deux en saisissant leurs identifiants Nextcloud. J'ai donc décidé de mettre en place une sanction plus dure pour les récidivistes : les jeter dans un puits sans fond, concrètement, une blackliste définitive au niveau du pare-feu OpenBSD. ![Prison de Bane](/images/2017/darkknight-prison.jpg) J'ai appliqué une logique similaire à *vilainreport*. Je réinjecte le rapport dans un petit shell script **supervilain** qui identifie les récidivistes et les jette dans le puits, où il resteront... jusqu'au prochain redémarrage du serveur. Voici le script en Korn Shell : ```shell #!/bin/ksh if [ $# != 1 ]; then echo "Usage: $0 logfile" exit 1 fi file=${1--} while read line do line=`echo $line | tr -d '\r'` if [[ $line = IP* ]]; then ipend="${line##+(IP )}" ip="${ipend%%+( ):*}" count="${ipend##*\: }" if [ "$count" -gt "2" ]; then echo "Ban supervilain ${ip} (${count})" `pfctl -t supervilain -T add ${ip}` fi fi done <"$file" ```