En jouant avec les tickets Kerberos, j'ai découvert un problème qui me permettait de m'authentifier auprès d'autres domaines au sein d'une forêt Active Directory (AD) à travers des trusts externes non-transitifs. Cela signifie qu'il n'existe pas d'« approbation non transitive ». Ce terme est au mieux trompeur et offre aux administrateurs de systèmes un faux sentiment de sécurité. Dans le cadre du problème discuté dans cet article, les attaquants peuvent s'authentifier à d'autres domaines à travers une approbation non transitive et potentiellement élever les privilèges dans la forêt du domaine de confiance. Ce billet détaille le problème découvert.
Après avoir signalé ce problème à Microsoft, j'ai reçu la réponse suivante :
Microsoft ayant déterminé que ce problème n'affectait pas la sécurité et ne prévoyant donc pas de modifier ce comportement, il n'y a aucun moyen d'éviter ce problème, si ce n'est de ne pas utiliser des approbations externes.
Approbations et transitivité
Note : Ce billet suppose une connaissance de base des approbations et de leur fonctionnement. (Pour plus d'informations sur ces sujets, je suggère de lire l'excellent article de Will Schroedersur les approbations). Ce billet ne couvre pas les approbations intra-forêt (c'est-à-dire celles au sein d'une même forêt), sauf dans la mesure où elles s'appliquent au chemin d'attaque spécifique discuté, ni les approbations d'authentification sélective, qui sont incroyablement rares dans les environnements réels.
Les autres approbations sont des approbations de forêt et des approbations externes.
- Les approbations de forêt sont des approbations entre deux forêts. Plus précisément, il s'agit d'une approbation transitive entre les domaines racines de deux forêts. Tout utilisateur d'un domaine de l'approbation de forêt peut s'authentifier auprès de n'importe quel domaine de cette forêt.
- Les approbations externes sont des approbations entre deux domaines et sont non-transitives. Seuls les utilisateurs du domaine de confiance peuvent s'authentifier auprès du domaine approuvé(figure 2).
Microsoft décrit la transitivité de l'approbation comme suit :
La transitivité détermine si une approbation peut être étendue en dehors des deux domaines avec lesquels elle a été formée.
- Un approbation transitive peut être utilisée pour étendre les relations d'approbation avec d'autres domaines.
- Une approbation non transitive peut être utilisée pour refuser des relations d'approbation avec d'autres domaines.
Cette description est claire : en cas d'approbation non transitive, seuls les deux domaines concernés par l'approbation peuvent s'authentifier l'un l'autre, et pas au-delà.
Malheureusement, comme je le démontrerai dans ce billet, ce n'est pas le cas.
Configuration du laboratoire
Pour démontrer correctement le problème de l'approbation non transitive, j'ai mis en place le laboratoire avec plusieurs forêts multi-domaines qui partagent une approbation externe(Figure 3).
Cette configuration implique trois (3) forêts. Deux (2) des forêts contiennent trois (3) domaines. La troisième forêt contient deux (2) domaines. Les domaines semperis.lab et treetest.lab partagent une approbation externe bidirectionnelle non transitive(Figure 4).
Les domaines grandchild1.child1.semperis.lab et semperisaz.lab partagent également une approbation externe bidirectionnelle non transitive(figure 5).
Cette configuration permet de démontrer les implications et les limites de la question de l'approbation non transitive.
Fonctionnement de l'authentification croisée Kerberos
Pour vous authentifier auprès d'un service à travers une approbation en utilisant Kerberos, vous avez besoin d'un ticket de référence. Il s'agit d'un ticket demandé à votre contrôleur de domaine (DC) local pour le domaine étranger. Pour montrer comment les demandes de tickets sont effectuées entre les approbations, cette section se concentre sur la forêt semperis.lab. Cependant, ces informations sont applicables à tout chemin de confiance « autorisé ».
Note : Ce billet suppose une compréhension de base du flux normal d'authentification Kerberos. (Pour une explication détaillée de ce flux, voir l'article de Sean Metcalfintitulé Detecting Kerberoasting Activity). Le reste de l'article utilise Rubeus pour demander des tickets manuellement.
L'exemple le plus simple d'authentification croisée est l'authentification d'un service sur un domaine qui a une confiance directe avec le domaine local. La confiance que le domaine grandchild1.child1.semperis.lab a avec child1.semperis.lab(Figure 5) est un exemple de ce type d'approbation. Dans cette situation, après avoir obtenu un TGT initial, la première étape pour obtenir un ticket de service pour un compte dans grandchild1.child1.semperis.lab vers un service dans child1.semperis.lab est d'obtenir un ticket de référence pour child1.semperis.lab(Figure 6, Figure 7).
La requête a été faite à un DC (SGC1DC1.grandchild1.child1.semperis.lab) dans le domaine(grandchild1.child1.semperis.lab) local à l'utilisateur authentifiant(lowpriv). La requête a été faite pour le service krbtgt/child1.semperis.lab. Le fait que le ServiceRealm (srealm) soit le domaine local(grandchild1.child1.semperis.lab) dans le ticket résultant montre que ce ticket est une référence.
Cette référence peut maintenant être utilisée pour demander des tickets de service (ST) au DC étranger (SC1DC1.child1.semperis.lab) pour l'hôte de service/SC1DC1.child1.semperis.lab (Figure 8, Figure 9).
Pour aller plus loin, si un service sur le domaine racine de la forêt(semperis.lab) est requis, un ticket de référence pour ce domaine ne peut pas être demandé directement au domaine local (grandchild1.child1.semperis.lab). Un ticket de référence pour krbtgt/semperis.lab est demandé au DC local sgc1dc1.grandchild1.child1.semperis.lab. Cependant, le DC renvoie un ticket pour le service krbtgt/child1.semperis.lab, indiquant que ce renvoi concerne le domaine child1.semperis.lab, et non semperis.lab (Figure 10, Figure 11).
Vous pouvez voir ce problème en essayant d'utiliser ce ticket pour demander un ticket de service pour le domaine semperis.lab. Il en résulte une erreur AP_ERR_BAD_INTEGRITY. Cela est dû au fait que le ticket de référence est crypté avec l'approbation de clé pour l'approbation grandchild1.child1.semperis.lab->child1.semperis.lab. Les DC du domaine racine semperis.lab n'ont pas connaissance de cette clé et ne peuvent donc pas déchiffrer le ticket(Figure 12, Figure 13).
Pour demander un ticket de service pour le domaine racine semperis.lab, il faut d'abord demander un ticket de référence pour semperis.lab à un DC du domaine child1.semperis.lab, en utilisant ce renvoi. La Figure 14 et la Figure 15 montrent une demande faite au DC étranger(sc1dc1.child1.semperis.lab), utilisant le renvoi pour le domaine child1.semperis.lab pour demander un renvoi supplémentaire pour le domaine racine semperis.lab.
Notez que pour demander ce ticket, le champ /domaine cible est nécessaire. Par défaut, Rubeus utilise le domaine du ticket qui lui a été transmis pour remplir le domaine dans le TGS-REQ. Dans ce cas, ce domaine serait grandchild1.child1.semperis.lab et entraînerait une erreur ERR_WRONG_REALM car le domaine local du DC est child1.semperis.lab. Cette information sera importante dans la section suivante.
Enfin, cette référence résultante pour semperis.lab peut être utilisée pour demander des ticket de service pour le domaine semperis.lab. La figure 16 montre la demande de ticket de service faite par l'utilisateur lowpriv@grandchild1.child1.semperis.lab au DC SDC1.semperis.lab pour l'hôte SPN/SDC1.semperis.lab. Comme le chemin de confiance est autorisé, cette requête a abouti même si les deux domaines concernés n'ont pas d'approbation directe(Figure 17).
Cette méthode de demande de références pour les domaines d'approbation peut être suivie pour demander des ticket de service pour n'importe quel service dans n'importe quel domaine pour lequel le chemin d'approbation est autorisé.
Rendre l'approbation non transitive transitive
Comment est-il donc possible de traverser des approbations externes pour s'authentifier auprès de domaines qui devraient être interdits ?
Les domaines semperisaz.lab et grandchild1.child1.semperis.lab ont une approbation externe bidirectionnelle. Par conséquent, après avoir récupéré un TGT pour n'importe quel compte du domaine semperisaz.lab, il est possible de demander un ticket de référence pour grandchild1.child1.semperis.lab(figure 18, figure 19).
Cette référence peut être utilisée pour demander des ticket de service pour des services sur le domaine grandchild1.child1.semperis.lab. Cependant, une tentative d'obtenir un ticket de référence vers d'autres domaines au sein de la même forêt (par exemple, child1.semperis.lab) renvoie une erreur ERR_PATH_NOT_ACCEPTED, comme prévu(Figure 20).
Cette erreur se produit parce que le lien semperisaz.lab->granchild1.child1.semperis.lab n'est pas transitif. Par conséquent, le chemin de semperisaz.lab à child1.semperis.lab n'est pas autorisé(figure 21).
Cependant, vous pouvez demander un TGT local pour grandchild1.child1.semperis.lab. J'appelle cela un TGT local parce que, contrairement auticket de référence , qui a un ServiceRealm (srealm) de semperisaz.lab, le ServiceRealm de ce TGT est grandchild1.child1.semperis.lab(Figure 22, Figure 23).
En utilisant ce TGT local, il est maintenant possible de demander un ticket de référence pour child1.semperis.lab (figure 24, figure 25).
Vous disposez maintenant d'une référence utilisable pour demander des tickets de service pour child1.semperis.lab, en utilisant n'importe quel compte du domaine semperisaz.lab et sans modifier les approbations ou les comptes dans AD. Les Figure 26 et Figure 27 montrent une demande de ticket de service depuis le DC sc1dc1.child1.semperis.lab pour le service host/sc1dc1.child1.semperis.lab en tant qu'utilisateur lowpriv@semperisaz.lab.
En outre, cette méthode peut être utilisée pour passer d'un domaine à l'autre dans la même forêt que celle où se trouve grandchild1.child1.semperis.lab. Nous pouvons le démontrer en demandant un ticket de référence vers le domaine racine semperis.lab. Un ticket de référence a été demandé pour semperis.lab depuis le DC sc1dc1.child1.semperis.lab en tant qu'utilisateur lowpriv@semperisaz.lab (Figure 28, Figure 29).
Heureusement, cette méthode ne permet pas de passer d'une approbation à l'autre en dehors de la forêt (confiance externe ou de forêt). Comme le montre la Figure 3, le domaine racine semperis.lab a une approbation externe bidirectionnelle avec treetest.lab. Cette approbation peut être utilisée pour démontrer cette limitation (Figure 30, Figure 31).
Cela empêche au moins un attaquant utilisant cette méthode de passer d'une forêt à l'autre. Néanmoins, ce problème d'approbation non transitive est clairement utile pour les attaquants qui tentent d'élever leurs privilèges au sein d'une forêt à partir d'une autre approbation. Les attaquants pourraient demander des informations sur des domaines supposés non autorisés, demander des domaines plus sensibles ou des domaines avec une sécurité potentiellement plus faible, ou effectuer des attaques Kerberoasting ou des coercitions d'authentification NTLM sur des domaines supposés non autorisés.
Aller plus loin
Bien que les attaquants ne puissent pas aller plus loin en utilisant uniquement la méthode décrite dans cet article, ce problème pourrait ouvrir de nouveaux chemins d'attaque. J'ai précédemment écrit un article démontrant la possibilité de créer des comptes de machines à travers des approbations et les implications de cela. En incorporant cette méthode de saut de domaine à cette nouvelle méthode, il est possible de surmonter la limitation décrite à la fin de la section précédente.
En utilisant le référent récupéré pour semperis .lab (à la fin de la section précédente), il est possible de demander un ticket pour le service LDAP sur un DC dans semperis.lab. Ici, un ticket de service pour ldap/sdc1.semperis.lab a été demandé en utilisant le ticket de référence pour semperis.lab comme utilisateur lowpriv@semperisaz.lab (Figure 32, Figure 33).
Ce ticket de service peut être injecté et utilisé pour créer un compte machine directement dans semperis.lab si la configuration autorise les Authenticated Users, ce qui est le cas par défaut (Figure 34).
Cette action entraîne la création par le DC sdc1.semperis.lab du compte machine TestComp dans le domaine semperis.lab (Figure 35).
Le nouveau compte machine TestComp est un compte local dans le domaine semperis.lab. Vous pouvez maintenant récupérer un TGT pour ce compte machine (Figure 36, Figure 37).
Ce compte machine TGT est autorisé à demander un ticket de référence vers le domaine d'approbation treetest.lab. Le compte machine TGT peut être utilisé pour demander un ticket de référence pour le domaine treetest.lab depuis le DC SDC1.semperis.lab (Figure 38, Figure 39).
Enfin, le problème décrit dans ce billet peut être utilisé pour accéder au domaine inaccessible dsptest.lab. Tout d'abord, demandez un TGT local pour treetest.lab. Le TGT local est demandé en utilisant le ticket de référence pour treetest.lab comme le compte TestComp$@semperis.lab du DC TDC1.treetest.lab (Figure 40, Figure 41).
Ensuite, utilisez ce TGT local pour demander un ticket de référence pour dsptest.lab. Les figures 42 et 43 montrent qu'un ticket de référence a été demandé pour le domaine dsptest.lab depuis le DC TDC1.treetest.lab en tant qu'utilisateur TestComp$@semperis.lab.
Il est clair que la combinaison de ces deux méthodes pourrait permettre de pénétrer très profondément dans les infrastructures d'entreprise AD, en utilisant n'importe quel compte à faible privilège sur un domaine qui a une confiance externe dans n'importe quel domaine au sein d'une forêt.
Détection de la vulnérabilité de la transitivité de l'approbation
Malheureusement, compte tenu de la réponse de Microsoft, le seul moyen d'éviter ce problème est de supprimer les liens de confiance externes.
S'il n'est pas possible de supprimer toutes les approbations externes, vous devrez surveiller l'événement Windows 4769 (Un ticket de service Kerberos a été demandé). La première indication à rechercher est qu'un TGT local a été demandé à un compte situé dans une forêt différente (Figure 44).
Ici, le champ Account Domain est un domaine qui appartient à une autre forêt et le Service Name est krbtgt. Cet événement est suivi d'un autre événement 4769, qui demande un ticket de référence (Figure 45).
Ici, le domaine du compte est un domaine situé dans une autre forêt et le nom du service est un autre domaine situé dans la forêt locale.
Notez que ces deux événements peuvent se produire sur des DC différents au sein du même domaine. Il n'est pas nécessaire qu'ils se produisent sur le même DC. À ce stade, tous les tickets de service demandés (événement 4769) qui utilisent cette référence auront un domaine de compte qui contient un domaine qui ne devrait pas être autorisé à s'authentifier auprès du domaine local.
La surveillance de ces événements et la détection de ce type d'attaque feront l'objet d'une prochaine version de Semperis Directory Services Protector (DSP).
À qui pouvez-vous faire confiance ?
Comme vous pouvez le constater, la description officielle de l'approbation externe non transitive est trompeuse. En l'état, lorsque vous créez une approbation externe non transitive, vous devez accepter que n'importe quel compte du domaine d'approbation puisse s'authentifier auprès de n'importe quel domaine de la forêt entière dans laquelle réside le domaine d'approbation.
Comme démontré dans la section « Aller plus loin » de cet article, la meilleure pratique consiste à interdire aux utilisateurs authentifiés de créer des comptes de machine. Ne pas le faire n'expose pas seulement les domaines de la forêt à un risque plus élevé d'attaque, mais aussi tous les domaines (et la forêt dans laquelle ils résident) qui ont une approbation externe avec n'importe quel domaine de la forêt à un risque plus élevé en raison de la capacité de créer des comptes de machine à travers les approbations et l'authentification contre les domaines qui devraient être interdits. (Plus d'informations sur le quota de compte machine et sur la manière d'empêcher la création de comptes machine à faible privilège sont disponibles dans l'excellent article de Kevin Robertson « MachineAccountQuota is USEFUL Sometimes »).
J'espère que cet article informera les administrateurs de systèmes du risque réel que représente la mise en œuvre de l'approbation externe pour l'ensemble de la forêt.
Chronologie
- 4 mai 2022 : Création du dossier du MSRC
- 12 mai 2022 : Le statut du dossier est passé à « Examen/Repro ».
- 17 juin 2022 : Le statut du dossier est passé à « Développement » avec un e-mail indiquant la chose suivante : « Nous avons confirmé le comportement que vous avez signalé. Nous allons poursuivre notre enquête et déterminer comment résoudre ce problème ».
- 17 juin 2022 : Le statut du cas est passé à « Complet - Résolu ».
- 24 août 2022 : Commentaire laissé sur le dossier pour connaître son état d'avancement
- 2 septembre 2022 : Commentaire de suivi laissé sur le dossier pour connaître son statut
- 14 septembre 2022 : Envoi d'un e-mail de suivi pour connaître l'état d'avancement du dossier
- 29 septembre 2022 : réception d'un e-mail expliquant que le problème n'a pas été jugé comme affectant la sécurité.
- Le 7 mars 2023 : Divulgation publique
Remerciements
- Will Schroeder pour la création de Rubeus, sans lequel cette recherche n'aurait pas été possible.
- Toutes les personnes qui ont relu cet article et fourni un retour, y compris :
- Elad Shamir
- Harjinder Nijjar
- Andrew Schwartz
- Jonny Johnson
En savoir plus
Vous voulez en savoir plus sur la recherche en matière de sécurité AD ? Consultez ces articles.