14/11/2024

CybersécuritéInternet

Sécurité des applications web – Qu’est-ce qu’une vulnérabilité open redirect ?

I. Présentation

Nous allons aujourd'hui nous intéresser à une vulnérabilité web que l'on trouve fréquemment sur tout type d'application : l'open redirect ou « redirection ouverte ».

Il s’agit d’une vulnérabilité simple à comprendre comme à exploiter, mais qui peut avoir un impact important sur les utilisateurs d’une application web puisque son exploitation la plus classique permet de voler les identifiants des utilisateurs piégés.

Nous allons donc étudier cette attaque notamment afin de comprendre son fonctionnement, ses impacts, sa détection et des pistes pour vous en protéger efficacement.

II. Tout savoir sur les open redirect

A. Redirection ouverte : qu'est-ce que c'est ?

Une vulnérabilité open redirect, qui signifie en français redirection ouverte, consiste à exploiter une fonction de redirection d'une application web afin de rediriger l'utilisateur ciblé vers n'importe quelle ressource du choix de l'attaquant.

De nos jours, l'exemple le plus classique dans lequel on trouve une redirection automatique est celui de l’accès direct aux fonctions d'un site web qui sont accessibles uniquement après authentification, sans être authentifié. L'utilisateur qui souhaite directement accéder à une telle fonction suivra le processus suivant :

Schéma d’une redirection classique intra-site.
Schéma d’une redirection classique intra-site.

Ici, l’application se sert du paramètre "redirect" pour se souvenir de l’endroit où souhaitait initialement se rendre l’utilisateur. Une fois que celui-ci est authentifié, il consulte le contenu de ce paramètre et y rediriger l’utilisateur.

On retrouve également beaucoup ce genre de comportement dans les mécanismes de SSO (authentification unique), dans lesquels l'authentification est gérée par une application tierce (pas sur le même nom de domaine), qui elle-même gère plusieurs autres applications. Dans ces cas de figure, il faut bien que l'application SSO puisse savoir sur quel site web rediriger l'utilisateur après authentification, on retrouve ainsi ces mécanismes de redirection.

Dans le cadre d'une vulnérabilité open redirect, l'application web ne vérifie pas correctement le contenu du paramètre redirect et redirigera l'utilisateur vers le site web indiqué dans tous les cas :

 Schéma d’exploitation d’une open redirect.
Schéma d’exploitation d’une open redirect.

Voici un exemple de code PHP très simple correspondant à ce cas de figure :

# Code PHP vulnérable à une open-redirect
$redirect_url = $_GET['redirect'];
header("Location: " . $redirect_url);

Ici, la page PHP réceptionne le paramètre "redirect" et l’utilise directement sans contrôle ni filtrage pour générer une redirection à l’aide de l’en-tête de réponse "Location".

Les attaquants utilisent donc ces liens pour cibler des utilisateurs dans des campagnes de phishing et d'ingénierie sociale. Le fait est que quand un utilisateur reçoit un lien (mail, chat ou autre), il peut, avec de la chance, avoir la présence d'esprit de regarder la présence du "https://", puis le nom de domaine qui suit, mais il ne regardera pas forcément les paramètres de la requête.

Or, si l'application "https://instagram.com" contient une vulnérabilité open redirect, l'attaquant en profitera pour envoyer l'utilisateur sur un site web tiers dont il a le contrôle en profitant du crédit que l'utilisateur accorde à "https://instagram.com", totalement légitime, pour le piéger. Par exemple :

Exemple de message de phishing exploitant une open redirect.
Exemple de message de phishing exploitant une open redirect.

L'utilisateur va bien se rendre dans un premier temps sur Instagram, mais sera ensuite immédiatement redirigé vers "https://insta-phish.com". Dans les cas les plus classiques, le site web de destination est une copie conforme du premier, sur lequel l'utilisateur non aguerri va s'authentifier puisque le site web ressemblera effectivement à celui sur lequel il pensait initialement atterrir.

B. Quels sont les risques et impacts d'une open redirect ?

Dans la plupart des cas, les attaquants utilisent les vulnérabilités open redirect afin de dérober les identifiants des utilisateurs piégés. Ils profitent, en effet, du fait que l'utilisateur, même vigilant, ira bien sur le lien fourni, car il s'agira effectivement du bon site web (ce qui est vrai !). Mais après avoir cliqué, celui-ci se trouvera redirigé sur un site web piégé sous contrôle de l'attaquant.

Le risque principal est donc le vol de compte, mais il s’agira bien d’un danger également pour le propriétaire du site. Bien que l’attaquant puisse faire le choix de rediriger ses victimes vers un site piégé représentant n’importe quelle application connue, il aura plus de chance de succès s’il les redirige vers une copie conforme du site initialement vulnérable.

Plus rarement, les attaquants peuvent également se servir des vulnérabilités open redirect pour faire effectuer à sa victime des actions sans leur consentement, cela en profitant du contexte authentifié dans lequel elle se trouve lorsqu’elle clique sur le lien. Ce type d’exploitation est rendu possible lorsque la même application possède d’autres faiblesses comme l’absence de jeton anti-CSRF couplée à l’utilisation de paramètres GET.

Pour illustrer ce type d’exploitation, supposons que votre application web possède un point d’entrée "/supprimer-compte.php?valider=oui", l’attaquant pourra faire le choix de rediriger l’utilisateur sur ce point d’entrée via la vulnérabilité open redirect. L’utilisateur se retrouvera donc à supprimer immédiatement son compte sans le vouloir.

Dans bien des cas, une vulnérabilité open redirect permet de faciliter la réalisation d’une attaque plus complète lorsqu’elle est couplée à d’autres vulnérabilités, également difficiles à exploiter seules. On peut notamment mentionner certaines vulnérabilités XSS, il s’agit d’injections de code HTML et JavaScript qui ne peuvent être exploitées que lorsque l’utilisateur consulte une ressource précise générée par l’attaquant. L’utilisation d’une open redirect peut alors servir à forcer un utilisateur à consulter cette ressource piégée.

III. Chercher et trouver des vulnérabilités open redirect

A. Identifier les pages et paramètres de redirection

Pour savoir si votre application web possède une vulnérabilité open redirect, il faut commencer par partir à la recherche des fonctionnalités de redirection qu’elle peut contenir. Comme nous l’avons vu, les cas les plus classiques de fonctionnalités contenant des redirections sont :

  • Les liens de redirection après une authentification : par exemple, après avoir saisi les identifiants, l'utilisateur est redirigé vers une page spécifique.
  • Les liens de confirmation d'inscription : un lien envoyé par e-mail qui redirige l'utilisateur vers une page de confirmation.
  • Les pages de redirection après une action : par exemple, après la soumission d'un formulaire, la validation d'une action, notamment pour les processus à plusieurs étapes.
  • Les pages d'erreur personnalisées : parfois, les pages d'erreur redirigent l'utilisateur vers une page d’aide ou qui expose des détails concernant le contexte de l’erreur. Ces cas de figure utilisent parfois des redirections pour rediriger vers la bonne page.
  • Les mécanismes de logout (déconnexion) : certaines applications redirigent l'utilisateur après la déconnexion (par exemple, vers la racine du site web).

Il ne s’agit bien sûr pas d’une liste exhaustive et il ne faut pas oublier que les frameworks de développement et CMS peuvent, eux aussi, apporter leurs propres fonctions et pages de redirection.

Dans les faits, il est très probable que ce type de redirection utilise des paramètres contenant des mots clés tels que "url", "redirect", "location", "next", "dest", "target", etc. Si vous avez un accès au code de l’application à sécuriser, vous pourrez effectuer une recherche sur ces mots clés pour identifier rapidement ce type de fonctionnalités.

Enfin, vous pouvez également tenter d’identifier ces fonctionnalités en tentant de joindre des pages ou en utilisant des paramètres classiques. L’idée est de dresser une liste de paramètres communs pour les fonctions de redirection, puis de les utiliser sur toutes les pages d’un site web et de constater si oui ou non, nous sommes effectivement redirigés ensuite (en commençant par cibler le site web lui-même). Vous pourrez trouver une grande liste de payloads sur le dépôt Github PayloadAllTheThing qui référence les cas classiques et connus de présence d’une open redirect :

Voici un extrait pour illustrer à quoi ressemblent ces différents payloads :

/{payload}
?next={payload}
?url={payload}
?target={payload}
?rurl={payload}
?dest={payload}
?destination={payload}
?redir={payload}
?redirect_uri={payload}
?redirect_url={payload}
?redirect={payload}
/redirect/{payload}
/cgi-bin/redirect.cgi?{payload}
/out/{payload}
/out?{payload}
?view={payload}

Une fois que les paramètres, pages et points d’entrées de redirection ont été identifiés, il est temps de passer à l‘étude de leur fonctionnement.

B. Évaluer la robustesse d’une fonctionnalité de redirection

Nous allons à présent voir comment évaluer la robustesse d’une fonctionnalité de redirection et tenter d’y détecter la présence d’une vulnérabilité open redirect. L’idée est de comprendre au travers des tests successifs ce qui est permis ou non par le code et les mesures de sécurité de l’application. Prenons le cas classique cité plus haut :

https://monapplication.tld/login?redirect=https://monapplication.tld/mon-profil

Le test le plus simple est bien sûr de renseigner un nom de domaine totallement différent au paramètre "redirect "et de constater ou non une redirection :

https://monapplication.tld/login?redirect=https://google.com

Si aucune protection n’est en place, vous vous retrouverez très rapidement sur "google.com". C’est en général là que l’on prend conscience que l’attaquant n’a qu’à envoyer un lien contenant son propre site pour que l’utilisateur y soit redirigé très discrètement, alors que le lien qu’il reçoit commence bien par "https://monapplication.tld".

Si une protection est en place, vous aurez différents comportements :

  • Soit le site affiche une erreur indiquant un refus de traitement
  • Soit l’application web redirige l’utilisateur vers sa page par défaut, comme la page d’accueil

Il faut se poser la question de ce que vérifie réellement l’application côté serveur, est-ce la présence du nom de domaine "monapplication" ou alors "monapplication.tld" ? Est-ce que cette chaîne de caractère peut être n’importe où pour que le test soit validé ?

https://monapplication.tld/login?redirect=https://attaquant.tld/monapplication.tld

Est-ce que l’utilisation d’un sous-domaine du même nom relié à un domaine qui n’a rien à voir permet de contourner les vérifications en place ? Dans ce cas de figure, l'attaquant va utiliser un domaine dont il a le contrôle et simplement créer un sous-domaine contenant le nom attendu :

https://monapplication.tld/login?redirect=https://monapplication.tld.attaquant.tld/

Également, comment réagit l’application si elle reçoit des URL non attendues comme :

redirect=ftp://monapplication.tld.attaquant.tld/
redirect=https://
redirect=attaquant.tld
redirect=////attaquant.tld
redirect=https://monapplication.tld&redirect=https://attaquant.tld/

Qu’en est-il du cyrillique, d’un nom de domaine de 300 caractères, d’une adresse IP, de "mon….application….tld.attaquant.tld" ? Chaque test réalisé doit vous permettre d’exclure un cas de figure précis, de savoir si oui ou non l’application vérifie côté serveur le nombre de paramètres, la présence de tel ou tel élément à tel endroit, etc.

Il peut aussi être intéressant de voir si l’application accepte de rediriger l’utilisateur sur n’importe laquelle de ses propres pages, cela afin de couvrir le cas du point d’entrée "/supprimer-compte.php?valider=oui", cité précédemment.

Les exemples cités dans cet article ne sont bien sûr pas exhaustifs. Mais, l’idée est de vous faire comprendre la complexité de tester tous les cas de figure. En sachant que chaque détail peut changer d’une technologie à une autre et en fonction des règles de pare-feu ou expressions régulières en place.

IV. Vulnérabilité open redirect: quelles bonnes pratiques ?

Maintenant que nous en savons plus sur les vulnérabilités open redirect, leurs impacts et comment les identifier, attardons-nous sur les bonnes pratiques de développement et de sécurité les concernant. Voici les principales bonnes pratiques à respecter dans une fonction de redirection d’une application web :

  • Éviter les redirections : la meilleure solution reste de ne pas utiliser les redirections si elles ne sont pas strictement nécessaires. Cela permettra à coup sûr d’éviter toute manipulation, mais cela n’est pas toujours possible.
  • Validation des URL : lorsque les redirections sont nécessaires, il est nécessaire de contrôler très strictement la valeur du paramètre utilisé afin qu’il ne sorte pas du contexte d’utilisation prévu et a minima que la chaîne de caractère commence bien par "http://monapplication.tld/". La difficulté ici réside dans la gestion des multitudes de possibilités permises et la complexité de composition d’une URL.
  • Utiliser des URL relatives : il est également possible de n’autoriser que les URL relatives, c’est-à-dire "?redirect=/login" au lieu de "?redirect=https://monapplication.tld/login". Ainsi, le code côté serveur devra systématiquement préfixer la valeur reçue avec son nom de domaine après s’être assuré de la validité du paramètre reçu.
  • Liste blanche de destinations : une méthode plus sûre consiste à utiliser une liste blanche d’URL avec laquelle devra parfaitement matcher l’entrée reçue. Cela garantit que seules les URL préapprouvées peuvent être utilisées pour les redirections. Idéalement, la comparaison se fera via un hash (exemple SHA256) et non grâce à une expression régulière qui peut contenir des failles et des erreurs.
  • Ajouter une couche d’abstraction : dans le cas où une fonction peut rediriger vers plusieurs URL en fonction du contexte, mais que toutes sont connues à l’avance, il est recommandé d’utiliser un tableau d’association "ID-URL" côté serveur. Ainsi l’utilisateur ne pourra fournir qu’un identifiant (idéalement un UUID) tel que "redirect=ee540842-54e4-410c-88c8-6e31948b6c1d" et c’est côté serveur que se fera l’association avec l’URL vers laquelle il sera redirigé. Cela évite toute possibilité de manipulation.
  • Avertir l’utilisateur qu’il quitte votre application web : dans le cas où l’utilisation d’une fonction de redirection sans restriction est intentionnelle, il est conseillé de mettre en place une page intermédiaire d’avertissement à l’utilisateur, afin qu’il soit bien au courant qu’il se dirige vers une autre application. C’est, par exemple, ce qui est proposé par le site HackerOne et de nombreux autres (exemple avec ce lien) :
Avertissement précédant le suivi d’un lien en redirection ouverte (HackerOne).

En résumé, l’idée autour des correctifs reste la même que pour une grande majorité de vulnérabilités : réduire la surface d’attaque et ne pas faire confiance aux entrées utilisateur.

V. Cas réels d’open redirect

Je vous partage ici différents rapports publics de bug bounty mentionnant des open redirects, vous pourrez ainsi constater qu’il existe des cas très simples et parfois plus complexes.

Le premier cas concerne une vulnérabilité découverte sur le site Semrush  (Source : Hackerone/report/311330). Ici, l’utilisation simple et classique du paramètre "?url=" en indiquant un nom de domaine tiers suffisait à rediriger l’utilisateur vers le site web voulu par l’attaquant :

Rapport concernant la découverte d’une open redirect classique sur SemRush – HackerOne.
Rapport concernant la découverte d’une open redirect classique sur SemRush – HackerOne.

On peut notamment voir dans la preuve fournit par le chercheur l’en-tête "Location" du serveur dans sa réponse 302 Found que l’utilisateur est bien redirigé vers l’URL spécifiée :

 Preuve de l’exploitation réussie d’une open redirect – HackerOne.
Preuve de l’exploitation réussie d’une open redirect – HackerOne.

Un autre cas plus complexe peut être consulté sur un rapport public du bug bounty Omise  (Source : HackerOne – reports/504751) :

Exemple d’open redirect via URL rewrite – HackerOne.
Exemple d’open redirect via URL rewrite – HackerOne.

Ici, le chercheur a inséré la chaîne de caractère "/%2f%2f%2fbing.com%2f%3fwww.omise.co" (c’est-à-dire "///bing.com?omise.co/?" une fois décodée) au beau milieu d’une URL, ce qui lui a permis d’être effectivement redirigé vers bing.com. La particularité ici est que l’exploitation passe par le traitement de l’URL entière par une fonction d’URL Rewrite, et non via la manipulation d’un paramètre spécifique. Cette découverte a valu à son auteur une prime de 100$.

Je vous invite à explorer les rapports publics de bug bounty pour en découvrir plus sur les nombreux cas de figure référencés de ce type de vulnérabilité :

VI. Conclusion

Nous avons abordé dans cet article les vulnérabilités open redirects (redirections ouvertes) qui, bien que simples à comprendre et à exploiter, peuvent avoir des conséquences significatives pour les utilisateurs d’une application web. En détournant une fonction de redirection automatique, un attaquant peut rediriger un utilisateur vers un site malveillant, facilitant ainsi des attaques comme le vol d'identifiants via le phishing.

Nous avons notamment fait le tour du fonctionnement de l'open redirect, ses risques, et exploré des méthodes pour identifier et prévenir ces vulnérabilités comme l'utilisation d'URL relatives ou l'implémentation de listes blanches pour valider les redirections autorisées.

author avatar
Mickael Dorigny Co-founder
Co-fondateur d'IT-Connect.fr. Auditeur/Pentester chez Orange Cyberdéfense.
Partagez cet article Partager sur Twitter Partager sur Facebook Partager sur Linkedin Envoyer par mail

Laisser un commentaire

Votre adresse e-mail ne sera pas publiée. Les champs obligatoires sont indiqués avec *

Ce site utilise Akismet pour réduire les indésirables. En savoir plus sur comment les données de vos commentaires sont utilisées.