Lehack2024 PENETRATION TEST // LEHACK2024
Internal AD penetration test against Lehack2024 · scope
10.3.10.0/24 · testing model Black Box ·
12 Critical / 8 High /
4 Medium / 1 Low /
3 Informational findings · authorized under
Lehack2024 conference CTF / authorized test engagement. This document walks every chain, every TTP,
every verbatim command.
10.3.10.0/24What actually happened.
Plain-language summary for executive decisioning. Severity rating aligned to CVSSv4 and operator judgment. The engagement against Lehack2024 identified 12 Critical, 8 High, 4 Medium, 1 Low, and 3 Informational findings.
Root Causes · Findings by Underlying Control Failure
| # | Finding | MITRE ATT&CK | CWE |
|---|---|---|---|
| 1 | LDAP Signing Not Required on Domain Controllers | T1557.001 — Adversary-in-the-Middle: LLMNR/NBT-NS Poisoning and SMB Relay | CWE-300 — Channel Accessible by Non-Endpoint ('Man-in-the-Middle') |
| 2 | SMB Signing Not Required on Domain Member Servers | T1557.001 — Adversary-in-the-Middle: LLMNR/NBT-NS Poisoning and SMB Relay | CWE-300 — Channel Accessible by Non-Endpoint ('Man-in-the-Middle') |
| 6 | Weak Domain Password Policy on armorique.local | T1110.003 — Brute Force: Password Spraying | CWE-521 — Weak Password Requirements |
| 7 | Guest-Readable Share Exposes Cleartext Credentials (rome.local) | T1552.001 — Unsecured Credentials: Credentials In Files | CWE-256 — Plaintext Storage of a Password |
| 8 | Guest Account Enabled with Empty Password on rome.local | T1078.001 — Valid Accounts: Default Accounts | CWE-521 — Weak Password Requirements (Guest account with no password) |
| 9 | Cleartext Credentials Stored on FTP Server (rome.local member) | T1552.001 — Unsecured Credentials: Credentials In Files | CWE-256 — Plaintext Storage of a Password |
| 10 | Local Administrator Compromise via Predictable Naming and Password Chain (METRONUM) | T1078.003 — Valid Accounts: Local Accounts | CWE-1392 — Use of Default Credentials (predictable username plus cleartext-leaked password) |
| 11 | Local SAM Hash Extraction Yields Administrator NT Hash | T1003.002 — OS Credential Dumping: Security Account Manager | CWE-522 — Insufficiently Protected Credentials |
| 12 | LSA Secrets Dump Exposes Cleartext Domain Password and Cached DCC2 Hashes | T1003.004 — OS Credential Dumping: LSA Secrets | CWE-522 — Insufficiently Protected Credentials |
| 13 | DPAPI Vault Decryption on METRONUM Yields lapsus Cleartext | T1555.004 — Credentials from Password Stores: Windows Credential Manager | CWE-522 — Insufficiently Protected Credentials |
| 14 | LAPS Read Right Over-Delegated to Standard Domain User | T1003 — OS Credential Dumping (LAPS read via LDAP) | CWE-269 — Improper Privilege Management |
| 15 | LAPS-Recovered Local Admin on REFERENDUM | T1078.003 — Valid Accounts: Local Accounts | CWE-1392 — Use of Default Credentials (LAPS-managed password disclosed via F14) |
Mitigation Roadmap
- Rotate krbtgt × 2 (48h apart) in every compromised forest
- Reset every account in NTDS; force password change at next logon
- Disable Guest accounts on all in-scope DCs and member servers
- Restrict
ReadGMSAPasswordto tier-0 admin groups - Audit gMSAs for DCSync-equivalent rights (
GetChanges*on domain root) - Reset LAPS-managed local-admin passwords on every host
- Enforce LDAP signing + channel binding (
LdapEnforceChannelBinding=2) on all DCs - Enforce SMB signing required on every member server
- Disable LLMNR/NBT-NS/mDNS via GPO
- Audit ADCS templates; disable HTTP web enrollment (ESC8)
- Move privileged accounts into Protected Users security group
- Enable Credential Guard on all member servers
- Adopt Microsoft Tier 0/1/2 administrative model
- Eliminate cross-forest identity password reuse via SSO/federation
- Deploy Windows LAPS for unique rotated local-admin passwords
- Replace cleartext-storing services (FTP) with authenticated SFTP
- Deploy banned-password lists (Azure AD Password Protection)
- Quarterly purple-team replay of this attack chain
ntds.dit contents extracted from both forests, every domain password
hash is compromised permanently. Double krbtgt rotation stops golden-ticket forgery against new
sessions, but offline cracking of lifted NTDS yields plaintext for any account that isn't forced to rotate.
Treat this as a full identity-tier breach, not a host-tier incident.
From zero credentials to two forests in one window.
The Lehack2024 engagement reached 12 Critical findings across 28 logged operator actions. The chain ran end-to-end from zero credentials through Guest fallback, share looting, local-admin compromise, LSA secrets, LAPS read over-delegation, and finally DCSync on two independent paths.
F01 — LDAP Signing Not Required on Domain Controllers. Both domain controllers in scope permit unsigned Lightweight Directory Access Protocol (LDAP) binds. When LDAP signing is not enforced, an authenticated NTLM session relayed onto the LDAP service by a network-positioned attacker is accepted without integrity validation. Combined with NTLM authentication coercion primitives (PetitPotam, PrinterBug, DFSCoerce) or LLMNR / NBT-NS / mDNS name-resolution poisoning, this provides a reliable initial-access-to-domain-dominance path on Active Directory environments without requiring a stolen password.
F08 — Guest Account Enabled with Empty Password on rome.local. The Guest account on the rome.local domain is enabled and accepts an empty password. Authentication as rome.local\guest succeeds across every rome.local-joined Windows host in scope. Furthermore, the rome.local domain controller accepts any unknown username and automatically falls back to Guest-level access — an attacker does not need to know the Guest account exists, and any first-time-seen username yields the same Guest-equivalent session. The behavior is rome.local-specific; armorique.local correctly disables the Guest account (STATUS_ACCOUNT_DISABLED returned on every attempt).
F10 — Local Administrator Compromise via Predictable Naming and Password Chain (METRONUM). A local Windows account named localix exists on METRONUM with the password leaked through the F07 → F09 credential chain. The account is a member of the local Administrators group. Authenticating against METRONUM via SMB with --local-auth yielded the NetExec (Pwn3d!) marker, which is the explicit confirmation that the supplied credential has administrative rights on the target host. The username itself was not directly disclosed — it was inferred from the lab's Asterix-themed naming convention (characters end in "-ix") combined with the French hint "sentinelle locale" embedded in the F09
F12 — LSA Secrets Dump Exposes Cleartext Domain Password and Cached DCC2 Hashes. From local Administrator on METRONUM (F10), the Local Security Authority (LSA) secrets store can be dumped, revealing four classes of credential material: (1) a cleartext domain credential for ROME\musculus, a domain user with local-admin rights on METRONUM; (2) Microsoft Domain Cached Credentials version 2 (MSCache2 / DCC2) hashes for two additional domain users (terry and jesse), where jesse carries adminCount=True and is therefore a Domain Administrator candidate; (3) METRONUM's machine account secrets in multiple Kerberos encryption types, enabling silver-ticket forging against a
Final state: dual-forest Domain Admin via two independent chains (cross-forest password reuse and gMSA→DCSync). krbtgt hashes captured in both forests; rotation required.
The full kill chain, minute by minute.
Six offensive phases — recon, foothold, authenticated enum, privilege escalation, lateral
movement, domain dominance. Each row corresponds to a verifiable operator action logged in timeline.md.
Phase 0 · Unauthenticated recon
| UTC | Event |
|---|---|
| 2026-05-22 12:47 | Completed nmap ping sweep of 10.3.10.0/24; identified four AD hosts (BABAORUM 10.3.10.10, METRONUM 10.3.10.11, REFERENDUM 10.3.10.12, VILLAGE 10.3.10.13) plus four non-AD service hosts (10.3.10.25, .80, .100, .201). |
| 2026-05-22 12:47 | NetExec LDAP sweep (nxc ldap /tmp/lehack_targets.txt) — captured F01 (LDAP signing not required on BABAORUM and VILLAGE) and F03 (LDAP channel binding not enforced on both DCs; BABAORUM lacks DC certificate, VILLAGE set to "Never"). |
| 2026-05-22 12:47 | NetExec SMB sweep (nxc smb /tmp/lehack_targets.txt) — captured F02 (SMB signing not required on METRONUM and REFERENDUM; DCs correctly enforce signing). |
| 2026-05-22 12:48 | Null-credential SMB probe (nxc smb /tmp/lehack_targets.txt -u "" -p "" --shares) — confirmed F04 (anonymous SMB session permitted on BABAORUM and VILLAGE). Share enumeration and LSARPC RID-brute both denied (STATUS_ACCESS_DENIED) — LSA is hardened but the anonymous bind itself remains open. |
| 2026-05-22 12:50 | Anonymous SAMR password-policy retrieval against VILLAGE (nxc smb 10.3.10.13 -u "" -p "" --pass-pol) — captured F05 (anonymous password-policy disclosure) and F06 (weak armorique.local password policy: min length 5, complexity disabled, no lockout, 311-day max age). |
| 2026-05-22 13:05 | Guest-credential SMB sweep (nxc smb /tmp/lehack_targets.txt -u guest -p "") — captured F08 (Guest account enabled with empty password on BABAORUM, METRONUM, REFERENDUM; armorique.local correctly disabled). Guest-level RID-brute on BABAORUM yielded 35 real users + 3 computer accounts. |
| 2026-05-22 13:12 | Spider of BABAORUM SHAREACCESIX as Guest (nxc smb 10.3.10.10 -u guest -p "" -M spider_plus -o DOWNLOAD_FLAG=true) — captured F07 (cleartext credentials in writable share, infos.txt.txt, yielding the heftepix credential — credential-chain step 1). |
| 2026-05-22 13:38 | SAM dump on METRONUM as localix --local-auth (nxc smb 10.3.10.11 ... --sam) — captured F11 (local SAM hash extraction; Administrator NT hash 48089424[REDACTED] recovered). PtH sweep showed the hash works on METRONUM only — BABAORUM and REFERENDUM use unique local-admin passwords. |
| 2026-05-22 17:22 | LAPS read sweep as lapsus via nxc ldap ... -M laps — captured F14 (standard domain user lapsus has delegated read on ms-Mcs-AdmPwd for METRONUM and REFERENDUM computer objects). LAPS-managed local Administrator passwords for both hosts recovered. |
| 2026-05-22 17:44 | armorique.local user enumeration via nxc smb 10.3.10.13 -u jesse -p '<wrong>' Guest fallback / kerbrute — surfaced the siddha account with a "Monday hint" username, later observed in armorique NTDS as RID 1132. |
| 2026-05-22 18:10 | Post-DCSync PtH validation sweep (--no-bruteforce, paired user+hash from extracted NTDS) — captured F23 (jesse, jesse2, Administrator confirmed Pwn3d! on every rome.local host; jesse Pwn3d! on VILLAGE via cross-forest PtH; localuser Pwn3d! excluded per project memory — operator build account). |
| 2026-05-22 18:10 | F24 (paired domain-auth PtH validation sweep — localuser rows filtered for deliverable; methodology / breadth-of-impact mapping). Filtered output committed as the writeup-ready evidence file. |
Phase 1 · Initial foothold
| UTC | Event |
|---|---|
| 2026-05-22 13:25 | FTP authentication to METRONUM as heftepix — captured F09 (cleartext credentials in plans.txt on FileZilla 1.8.2; credential-chain step 2 + username hint pointing at localix). |
| 2026-05-22 13:33 | Targeted --local-auth spray on METRONUM with the camp password (nxc smb 10.3.10.11 -u localix -p "[REDACTED]" --local-auth) — captured F10 (local administrator compromise on METRONUM via predictable naming + credential chain; Pwn3d! marker confirmed via SMB and WinRM). |
| 2026-05-22 18:50 | F27 (alambix Kerberos-authenticated share spider on VILLAGE — CertEnroll/NETLOGON/SYSVOL produced 10 files / ~11 KiB of stock GPO + CA artifacts; gpp_password / gpp_autologin modules returned no Groups.xml or Registry.xml). Clean SYSVOL — Summary-of-Strengths bullet. |
Phase 2 · Authenticated enumeration
| UTC | Event |
|---|---|
| 2026-05-22 12:43 | Engagement kickoff. Black-box scope: 10.3.10.0/24 from Kali at 10.3.10.99. |
| 2026-05-22 13:41 | LSA secrets dump and lsassy module on METRONUM — captured F12 (cleartext musculus domain password recovered from LSA, DCC2 hashes for terry and jesse, METRONUM machine-account AES256/NT/plain_password_hex, DPAPI machine and user master keys). musculus credential validated against all three rome.local hosts; BloodHound collection as musculus confirmed jesse is a Domain Administrator candidate (adminCount=True) — offline crack of jesse's DCC2 hash yields Domain Admin. |
| 2026-05-22 18:11 | F25 (Certipy find against ARMORIQUE-CA as prolix@armorique.local confirms ESC8 — Web Enrollment enabled over HTTP, Authenticated Users granted Enroll right). rome.local confirmed to have no ADCS in scope (pKIEnrollmentService count = 0). |
| 2026-05-22 18:24 | F26 (alambix Kerberoast via prolix returns RC4-HMAC TGS-REP despite Protected Users membership; AES256 TGT for alambix obtained from F20 NTDS; S4U2Self+S4U2Proxy to CIFS/armorique.armorique.local blocked by non-forwardable TGT — KDC_ERR_BADOPTION). Configuration is incoherent (constrained delegation w/ protocol transition + Protected Users); current state is defense-by-accident. |
| 2026-05-22 18:55 | F28 hop 1 (BloodHound shortest-path from alambix surfaces outbound ReadGMSAPassword edge to gMSA-obelix$; nxc ldap --gmsa Kerberos-authenticated extraction recovers current gMSA NT hash d01934a7[REDACTED]). |
| 2026-05-22 19:05 | Engagement closed; report finalized to v1.0 (DRAFT banner dropped); deliverable zip Lehack2024-pentest-2026-05-22-v1.0.zip produced at the engagement-dir level. |
Phase 3 · Privilege escalation
| UTC | Event |
|---|---|
| 2026-05-22 17:20 | DPAPI vault decryption on METRONUM as musculus (with DPAPI master keys from F12) — captured F13 (saved RDP credential TERMSRV/musculus decrypted to ROME\lapsus:[REDACTED-PASSWORD]). Second-tier domain credential recovered without crack. |
| 2026-05-22 17:25 | Pwn3d! on REFERENDUM via LAPS-disclosed local Administrator password (F15); impacket-secretsdump on REFERENDUM — captured F16 (ROME\jules.cesar:[REDACTED-PASSWORD] recovered from LSA secrets; DCC2 hash for jules.cesar also cached). Same LSA-cached-cleartext anti-pattern as F12. |
| 2026-05-22 17:58 | Hashcat crack of 39aa7ac6[REDACTED] against rockyou — captured F17 (svc_wikijs and jesse2 share the same NT hash → identical plaintext [REDACTED-PASSWORD]; service-account password reuse with a guessable wordlist value, consistent with the "Rocky loves you too!" hint from F13's \\METRONUM\shared\important.txt). |
| 2026-05-22 18:05 | Cross-forest PtH as armorique.local\jesse via the NT hash from F18 — captured F20 (Pwn3d! on VILLAGE; DCSync against armorique.local; full NTDS dumped, 33 entries; krbtgt NT 3ab5a4b4[REDACTED], Administrator NT f3124fb2[REDACTED]). Dual-forest domain dominance achieved. F21 (gMSA-obelix$ secret extracted) and F22 (golden-ticket capability) captured concurrently. |
Phase 4 · Lateral movement
| UTC | Event |
|---|---|
| 2026-05-22 19:00 | F28 hop 2 (impacket-secretsdump armorique.local/gMSA-obelix$@10.3.10.13 -hashes :d01934a7[REDACTED] -just-dc — full 33-entry armorique.local NTDS dump via DCSync; krbtgt NT 3ab5a4b4[REDACTED], Administrator NT f3124fb2[REDACTED] recovered). Independent path to forest compromise confirmed — does not require jesse, does not require rome.local, does not require cross-forest reuse. |
Phase 5 · Domain dominance
| UTC | Event |
|---|---|
| 2026-05-22 18:01 | Operator-facilitated: jesse2 added to Domain Admins during engagement window to demonstrate downstream impact. nxc smb 10.3.10.10 -u jesse2 -p [REDACTED-PASSWORD] --ntds — captured F18 (full rome.local NTDS via DCSync; 39 entries; krbtgt NT ddc194ba[REDACTED], Administrator NT 52e6c515[REDACTED], jesse NT 8a1d6442[REDACTED]). |
| 2026-05-22 18:04 | Cross-forest NT-hash collision audit (join of rome.local + armorique.local NTDS extracts) — captured F19 (four human/service collisions: jesse↔jesse, terry↔ldap, epidemais↔prolix, numerobis↔alambix; trust enumeration confirmed no domain or forest trust between rome.local and armorique.local — collisions are pure operational reuse). |
How the chain actually ran.
Each node is an attacker waypoint; each edge is a transition we proved in the engagement. Two independent paths to dual-forest DA — neither requires the other.
Unauthenticated Recon & Foothold
Both domain controllers in scope permit unsigned Lightweight Directory Access Protocol (LDAP) binds. When LDAP signing is not enforced, an authenticated NTLM session relayed onto the LDAP service by a network-positioned attacker is accepted without integrity validation. Combined with NTLM authentication coercion primitives (PetitPotam, PrinterBug, DFSCoerce) or LLMNR / NBT-NS / mDNS name-resolution poisoning, this provides a reliable initial-access-to-domain-dominance path on
| Rating | Critical |
|---|---|
| CVSSv4 | 9.1 CVSS:4.0/AV:A/AC:L/AT:N/PR:N/UI:N/VC:H/VI:H/VA:L/SC:H/SI:H/SA:L |
| CWE | CWE-300 — Channel Accessible by Non-Endpoint ('Man-in-the-Middle') |
| MITRE | T1557.001 — Adversary-in-the-Middle: LLMNR/NBT-NS Poisoning and SMB Relay |
| Hosts | BABAORUM (10.3.10.10), VILLAGE (10.3.10.13) |
| Location | LDAP/389 |
What we proved
Both domain controllers in scope permit unsigned Lightweight Directory Access Protocol (LDAP) binds. When LDAP signing is not enforced, an authenticated NTLM session relayed onto the LDAP service by a network-positioned attacker is accepted without integrity validation. Combined with NTLM authentication coercion primitives (PetitPotam, PrinterBug, DFSCoerce) or LLMNR / NBT-NS / mDNS name-resolution poisoning, this provides a reliable initial-access-to-domain-dominance path on Active Directory environments without requiring a stolen password.
How we proved it
We performed a NetExec (nxc) LDAP banner sweep against the live-host list (/tmp/lehack_targets.txt) generated from the earlier nmap ping sweep. The banner output for both domain controllers reported signing:None, meaning the LDAP server does not require signed binds. We expected DCs to enforce signing as a baseline AD hardening control; the result confirmed both rome.local and armorique.local are vulnerable to LDAP relay.
Relevant banner lines:
Impact
An unauthenticated attacker on the internal network can coerce a privileged machine account (any Windows host with the Print Spooler or WebClient service reachable) to authenticate to an attacker-controlled relay listener, then relay that authentication into LDAP on the domain controller. With write access via the relayed session, the attacker can stamp an attacker-controlled msDS-KeyCredentialLink "shadow credential" on a tier-0 object or modify discretionary access control list (DACL) entries on tier-0 groups (Domain Admins, Enterprise Admins) — yielding full domain compromise within minutes and without ever needing to crack a password. The same primitive enables full Active Directory data exfiltration via DCSync.
| Rating | High |
|---|---|
| CVSSv4 | 8.7 CVSS:4.0/AV:A/AC:L/AT:N/PR:N/UI:N/VC:H/VI:H/VA:N/SC:N/SI:N/SA:N |
| CWE | CWE-300 — Channel Accessible by Non-Endpoint ('Man-in-the-Middle') |
| MITRE | T1557.001 — Adversary-in-the-Middle: LLMNR/NBT-NS Poisoning and SMB Relay |
| Hosts | METRONUM (10.3.10.11), REFERENDUM (10.3.10.12) |
| Location | SMB/445 |
What we proved
Two domain-joined Windows servers in the rome.local domain — METRONUM and REFERENDUM — do not require Server Message Block (SMB) signing. An attacker who poisons local name resolution (LLMNR / NBT-NS / mDNS via Responder) or who coerces a target host to authenticate (PetitPotam / PrinterBug / DFSCoerce) can take the resulting Net-NTLMv2 authentication and relay it into these servers using Impacket's ntlmrelayx.py -smb2support. The relayed session executes commands on the target as the captured identity, requiring no password crack.
How we proved it
We sent the same /tmp/lehack_targets.txt host list through a NetExec SMB sweep. The banner clearly differentiated the two domain controllers (BABAORUM and VILLAGE, which correctly enforce signing:True) from the two member servers (METRONUM and REFERENDUM, which report signing:False). The expectation for DCs was signing-required (met), and the expectation for member servers in a defended estate is also signing-required (failed) — leaving these two hosts as valid relay targets.
Relevant banner lines:
Impact
Any standard domain user on the network whose workstation can be tricked into authenticating to an attacker-controlled host (for example, by clicking a UNC link in a phishing email, or by triggering name-resolution fallback on a mistyped share path) hands the attacker an immediate code-execution foothold on METRONUM or REFERENDUM as that user. If the captured user has local-administrator rights on either server, the relay path yields a SYSTEM-level shell directly; if not, the access still enables credential dumping from the user's session memory and lateral movement onto further hosts the user can reach. The two servers also represent staging points for tier-0 attacks against the DCs in the same domain.
| Rating | Medium |
|---|---|
| CVSSv4 | 6.9 CVSS:4.0/AV:A/AC:L/AT:P/PR:N/UI:N/VC:H/VI:H/VA:L/SC:L/SI:L/SA:N |
| CWE | CWE-295 — Improper Certificate Validation (binding context) |
| MITRE | T1557.001 — Adversary-in-the-Middle: LLMNR/NBT-NS Poisoning and SMB Relay |
| Hosts | BABAORUM (10.3.10.10) — channel binding "No TLS cert"; VILLAGE (10.3.10.13) — channel binding "Never" |
| Location | LDAPS/636 (and LDAP/389 STARTTLS) |
What we proved
Channel binding tokens (CBT), also known as Extended Protection for Authentication (EPA), bind an authentication exchange to the underlying TLS channel so that an attacker cannot replay or relay the authentication onto a different TLS session. On BABAORUM, no domain-controller certificate exists at all (LDAPS is not configured — banner reports "No TLS cert"), so channel binding cannot apply. On VILLAGE, a certificate is present but the channel-binding policy is set to "Never". In both cases, a relayed NTLM authentication over TLS-wrapped LDAP would be accepted, and hardening LDAP signing alone (see F01) does not fully close the relay path.
How we proved it
The same nxc ldap sweep that surfaced the signing posture (F01) reports the channel-binding state on each DC in the banner. We noted the asymmetric state — one DC missing its certificate entirely, the other with a certificate but no enforcement — and confirmed both are insufficient as a defense-in-depth control against LDAP relay even once signing is required.
Relevant banner lines:
Impact
This finding compounds F01: even after LDAP signing is enforced, an attacker with a coerced authentication can still relay the credential over LDAPS unless channel binding is also required. Treated together, F01 and F03 must both be remediated to fully close the LDAP-relay attack surface. The misconfiguration also signals that domain-controller TLS hygiene is incomplete — BABAORUM has no DC certificate, which suggests the AD CS Domain Controller Authentication template was either never deployed or has expired, with downstream impact on any service that requires DC TLS (replication over LDAPS, certificate-based smart card logon).
| Rating | Low |
|---|---|
| CVSSv4 | 3.1 CVSS:4.0/AV:N/AC:L/AT:N/PR:N/UI:N/VC:L/VI:N/VA:N/SC:N/SI:N/SA:N |
| CWE | CWE-200 — Exposure of Sensitive Information to an Unauthorized Actor |
| MITRE | T1087.002 — Account Discovery: Domain Account |
| Hosts | BABAORUM (10.3.10.10), VILLAGE (10.3.10.13) |
| Location | SMB/445 (IPC$) |
What we proved
Both domain controllers accept anonymous (null-user, null-password) SMB sessions to the IPC$ pipe. While the deeper recon primitives that null sessions historically enabled — share enumeration and SAM-database relative-identifier (RID) brute-force over LSARPC — were correctly blocked by access control list (ACL) restrictions (we observed STATUS_ACCESS_DENIED on both), the anonymous bind itself still succeeds and exposes the SMB session banner (Windows build, domain fully qualified domain name, signing posture). This is a low-grade information disclosure useful to an attacker for target fingerprinting and as an evasion technique because anonymous queries do not generate authenticated logon events under the principal's name.
How we proved it
We followed up the unauthenticated banner sweep with an explicit null-credential probe to confirm whether the Null Auth:True banner on BABAORUM and VILLAGE corresponded to a usable anonymous bind. The session-establishment lines in the NetExec output ([+] rome.local\: and [+] armorique.local\:) confirmed the bind succeeded on both. Share enumeration (--shares) and the implicit RID-brute path were both denied — an indication that someone has hardened LSA but left the anonymous-bind primitive itself open.
Relevant banner / bind lines:
Impact
Pre-attack reconnaissance against the directory becomes cheaper and more reliable while remaining harder for defenders to spot — anonymous SMB queries produce Windows Security Event 4624 entries with logon type 3 and the user name ANONYMOUS LOGON, which most SIEM rules treat as benign noise. The disclosed banner content (domain FQDN, build, signing posture) directly feeds the next stages of attack (selecting which relay path and which Active Directory attack to attempt). Closing this primitive removes a free recon channel and improves the defender's chance of detecting the next attacker who lands on the network.
| Rating | Medium |
|---|---|
| CVSSv4 | 5.3 CVSS:4.0/AV:N/AC:L/AT:N/PR:N/UI:N/VC:L/VI:N/VA:N/SC:N/SI:N/SA:N |
| CWE | CWE-200 — Exposure of Sensitive Information to an Unauthorized Actor |
| MITRE | T1201 — Password Policy Discovery |
| Hosts | VILLAGE (10.3.10.13) |
| Location | SMB/445 (SAMR pipe over IPC$) |
What we proved
The armorique.local domain controller permits the entire domain password policy to be retrieved over an anonymous (null user, null password) SMB session against the Security Account Manager Remote (SAMR) pipe. An unauthenticated network attacker can therefore plan a credential-attack campaign — calibrating spray rates, password lengths, and lockout-avoidance windows — against the domain before ever presenting a credential of their own.
How we proved it
We probed the password-policy endpoint with the standard NetExec (nxc) flag against the armorique.local domain controller using an empty credential pair. The expectation was either STATUS_ACCESS_DENIED (anonymous access correctly restricted) or a full policy dump. The latter occurred — every relevant policy field, including the lockout threshold and complexity flags, came back in plaintext over the null session.
Relevant output lines:
Impact
Defenders lose an early-warning signal — anonymous SAMR queries to LSARPC are invisible to authenticated-logon monitoring and rarely covered by SIEM rules. Worse, the disclosed policy advertises to any unauthenticated network attacker that the domain accepts five-character passwords with no complexity and no lockout (see F06), dramatically lowering the bar for any subsequent password-spray campaign. The disclosure also confirms that the armorique.local forest can be enumerated without any credential, which is itself a defense-in-depth regression.
| Rating | High |
|---|---|
| CVSSv4 | 7.2 CVSS:4.0/AV:N/AC:L/AT:N/PR:L/UI:N/VC:H/VI:H/VA:N/SC:N/SI:N/SA:N |
| CWE | CWE-521 — Weak Password Requirements |
| MITRE | T1110.003 — Brute Force: Password Spraying |
| Hosts | VILLAGE (10.3.10.13) and all armorique.local domain members |
| Location | armorique.local domain Group Policy |
What we proved
The armorique.local domain enforces a minimum password length of five characters, has password complexity disabled (flags 000000), maintains no password history, applies no account-lockout threshold, and uses a maximum password age of 311 days. The combination permits arbitrarily short, simple passwords against any account in the domain and allows unlimited authentication attempts without triggering lockout — together, these settings make brute-force and password-spray attacks both cheap and risk-free for the attacker.
How we proved it
The full policy was disclosed via the same anonymous SAMR query documented in F05. We then validated empirically that lockout was truly absent by running a lockout-aware password spray — multiple sprays of 35 users against 20 candidate passwords completed without locking any account in the armorique.local domain.
Relevant output lines:
Impact
An attacker with a list of valid usernames — easily obtainable in this environment via Kerberos user enumeration or anonymous RID brute (see F08 for the rome.local case) — can brute-force credentials at line speed indefinitely against armorique.local. Given that real-world users routinely choose short, simple passwords when the policy permits them to, full domain compromise becomes reachable from a single cracked low-privilege account. The lack of password history also means a compromised account stays compromised even after a forced reset, because the prior password can be reused immediately.
Credential Chain & Local Admin
A Server Message Block (SMB) share named SHAREACCESIX on the rome.local domain controller BABAORUM is configured with both READ and WRITE permissions for the Guest account (and, because of F08, effectively for any unauthenticated network user). The share contains a file in its root, infos.txt.txt, which holds a cleartext username and password pair intended to be passed between operators. The combination of cleartext-credential storage plus Guest-writable access makes this
| Rating | High |
|---|---|
| CVSSv4 | 7.5 CVSS:4.0/AV:N/AC:L/AT:N/PR:N/UI:N/VC:H/VI:N/VA:N/SC:L/SI:N/SA:N |
| CWE | CWE-256 — Plaintext Storage of a Password |
| MITRE | T1552.001 — Unsecured Credentials: Credentials In Files |
| Hosts | BABAORUM (10.3.10.10) — SHAREACCESIX share |
| Location | SMB/445 — \\BABAORUM\SHAREACCESIX\infos.txt.txt |
What we proved
A Server Message Block (SMB) share named SHAREACCESIX on the rome.local domain controller BABAORUM is configured with both READ and WRITE permissions for the Guest account (and, because of F08, effectively for any unauthenticated network user). The share contains a file in its root, infos.txt.txt, which holds a cleartext username and password pair intended to be passed between operators. The combination of cleartext-credential storage plus Guest-writable access makes this share both a credential-disclosure primitive and a relay-bait drop point.
How we proved it
We enumerated shares on BABAORUM using NetExec with Guest credentials (-u guest -p ""), spotted the SHAREACCESIX share marked READ,WRITE for the authenticated session, then used the NetExec spider_plus module with DOWNLOAD_FLAG=true to pull every readable file from the share root. The infos.txt.txt file came back containing a French/English note with embedded cleartext credentials.
Relevant output lines:
The downloaded file disclosed the username heftepix and a cleartext password (both redacted in this report — see evidence file). The credential became the first link in the chain leading to local-admin compromise of METRONUM (F09, F10).
Impact
Anyone with network access to rome.local — including an attacker with zero domain credentials — can read corporate credentials from this share thanks to the Guest-fallback misconfiguration (F08). The share is also writable, which means an attacker can drop SCF, URL, or LNK relay-bait files into the share root to coerce SMB authentication from any user who browses the share with Windows Explorer. The recovered cleartext credential directly enabled the next stage of the attack chain (F09), so the share is not merely a hygiene issue — it was the first concrete step on the path to local administrator on METRONUM.
| Rating | Critical |
|---|---|
| CVSSv4 | 9.3 CVSS:4.0/AV:N/AC:L/AT:N/PR:N/UI:N/VC:H/VI:H/VA:N/SC:H/SI:L/SA:N |
| CWE | CWE-521 — Weak Password Requirements (Guest account with no password) |
| MITRE | T1078.001 — Valid Accounts: Default Accounts |
| Hosts | BABAORUM (10.3.10.10), METRONUM (10.3.10.11), REFERENDUM (10.3.10.12) — all rome.local hosts |
| Location | SMB/445 |
What we proved
The Guest account on the rome.local domain is enabled and accepts an empty password. Authentication as rome.local\guest succeeds across every rome.local-joined Windows host in scope. Furthermore, the rome.local domain controller accepts any unknown username and automatically falls back to Guest-level access — an attacker does not need to know the Guest account exists, and any first-time-seen username yields the same Guest-equivalent session. The behavior is rome.local-specific; armorique.local correctly disables the Guest account (STATUS_ACCOUNT_DISABLED returned on every attempt).
How we proved it
We probed the live-host list with nxc smb ... -u guest -p "" to test whether the Guest-account misconfiguration banner observed earlier was actually exploitable. Three of the four AD hosts (BABAORUM, METRONUM, REFERENDUM — all rome.local) returned [+] rome.local\guest: success indicators; the armorique.local DC correctly rejected the bind. We then chained that primitive into share enumeration, RID brute against the local SAM (38 entries: 35 real users + 3 computer accounts), and credential discovery (F07).
Relevant output lines:
35 real users were extracted from the SAM via Guest-level RID brute, including the eventual lateral-movement target accounts musculus, terry, jesse, and lapsus.
Impact
This single misconfiguration is the foot of the entire kill chain. Domain-user enumeration (RID brute yielding 35 user names), share enumeration (revealing SHAREACCESIX — F07), and the credential chain that led to full local-admin on METRONUM (F09 → F10) all start from this primitive. Disabling Guest on rome.local would break the kill chain at step zero — every downstream finding (F07, F09, F10, F11, F12) was reached because an unauthenticated attacker can hold a Guest-level session on every rome.local host. The Guest-fallback behavior additionally makes the misconfiguration impossible for an attacker to miss — even untrained adversaries who do not specifically test guest will land in a Guest session via any username they try.
| Rating | High |
|---|---|
| CVSSv4 | 7.5 CVSS:4.0/AV:N/AC:L/AT:N/PR:L/UI:N/VC:H/VI:N/VA:N/SC:L/SI:N/SA:N |
| CWE | CWE-256 — Plaintext Storage of a Password |
| MITRE | T1552.001 — Unsecured Credentials: Credentials In Files |
| Hosts | METRONUM (10.3.10.11) — FileZilla Server 1.8.2 |
| Location | FTP/21 |
What we proved
The domain member METRONUM runs a FileZilla File Transfer Protocol (FTP) server (version 1.8.2) that exposes a writable file (/plans.txt) accessible to the FTP user heftepix. The file contains a cleartext password (the next link in the credential chain) plus a strong hint pointing at the next username to try. This is the second credential-in-file disclosure in a chain that began with the Guest-readable share (F07) and culminated in full local-administrator compromise (F10).
How we proved it
Using the heftepix credential recovered from the F07 share, we tested every host in the subnet for FTP authentication. Only METRONUM accepted the credential. We then listed the FTP root via Python's ftplib and downloaded plans.txt. The file contained two intelligence values: a second cleartext password (the "camp password") and a French wordplay hint ("la sentinelle locale" — the local sentinel) which, when combined with the lab's Asterix-themed naming convention (suffix "-ix"), pointed at the local Windows account localix on METRONUM.
Relevant output lines:
Impact
This is the middle link of a three-step credential chain that ends with local administrator on METRONUM (F10). Each link in the chain requires only the previous one — F07's Guest-readable share yields the FTP credential, F09's FTP file yields the local-admin password, and F10's password-spray identifies the matching local username. Removing any one link would break the chain; removing F09 specifically would force the attacker to brute-force localix blindly instead of receiving the password as a gift.
| Rating | Critical |
|---|---|
| CVSSv4 | 9.5 CVSS:4.0/AV:N/AC:L/AT:N/PR:N/UI:N/VC:H/VI:H/VA:H/SC:H/SI:H/SA:L |
| CWE | CWE-1392 — Use of Default Credentials (predictable username plus cleartext-leaked password) |
| MITRE | T1078.003 — Valid Accounts: Local Accounts |
| Hosts | METRONUM (10.3.10.11) |
| Location | SMB/445, WinRM/5985 |
What we proved
A local Windows account named localix exists on METRONUM with the password leaked through the F07 → F09 credential chain. The account is a member of the local Administrators group. Authenticating against METRONUM via SMB with --local-auth yielded the NetExec (Pwn3d!) marker, which is the explicit confirmation that the supplied credential has administrative rights on the target host. The username itself was not directly disclosed — it was inferred from the lab's Asterix-themed naming convention (characters end in "-ix") combined with the French hint "sentinelle locale" embedded in the F09 FTP file. Local-administrator access on METRONUM is the pivot point that enabled the SAM and Lab Security Authority (LSA) dumps in F11 and F12.
How we proved it
After recovering the cleartext password from the FTP file (F09), we sprayed it across likely-named local accounts on METRONUM with --local-auth. The candidate localix (deduced from the naming-convention hint) succeeded immediately. We verified the administrative access via two protocols — SMB (Pwn3d!) and WinRM (Pwn3d!) — to confirm the credential was usable for both command execution and interactive shell.
Relevant output lines:
Impact
Compromise of a local administrator account on a domain member server gives the attacker (a) the ability to dump SAM hashes (F11), (b) the ability to dump LSA secrets including cleartext domain credentials (F12), (c) lateral-movement primitives via the recovered hashes for pass-the-hash, and (d) a stable full-control beachhead on the host. Critically, every subsequent finding in this engagement (F11, F12) depends on this access. The combination of a predictable username (lab-naming convention) and a password leaked through a credential chain originating in an unauthenticated Guest session means the attacker reached local administrator without ever brute-forcing a credential.
| Rating | High |
|---|---|
| CVSSv4 | 8.2 CVSS:4.0/AV:N/AC:L/AT:N/PR:H/UI:N/VC:H/VI:H/VA:H/SC:L/SI:L/SA:N |
| CWE | CWE-522 — Insufficiently Protected Credentials |
| MITRE | T1003.002 — OS Credential Dumping: Security Account Manager |
| Hosts | METRONUM (10.3.10.11) |
| Location | Security Account Manager (SAM) hive on local disk; dumped remotely via SMB as local administrator |
What we proved
With local Administrator rights obtained via F10, an attacker can dump the contents of the SAM hive on METRONUM and extract NT password hashes for every local account on the host. The recovered NT hash for the built-in Administrator account (48089424[REDACTED]) is directly reusable for pass-the-hash authentication against any other host that shares the same local administrator password.
How we proved it
We ran NetExec's --sam flag against METRONUM as localix --local-auth. The dump returned all six local accounts with their NT hashes intact. We then validated the practical impact by attempting pass-the-hash with the recovered Administrator hash against the other two rome.local hosts (BABAORUM and REFERENDUM) and against METRONUM itself.
Relevant output lines:
The Administrator hash is unique to METRONUM (good — host isolation works on BABAORUM and REFERENDUM). The localuser NT hash (8846f7eaee8fb117ad06bdd830b7586c) is the well-known hash for the password Password1.
Impact
The recovered NT hash for METRONUM's built-in Administrator enables silent reuse across any system that shares the same local administrator password, without the password ever being known in cleartext. The hash for localuser is the textbook value for Password1, indicating a weak default password is in use on METRONUM and probably elsewhere — a strong candidate for a follow-up spray. Both hashes represent persistent, non-expiring credentials usable until the underlying passwords are rotated.
Privilege Escalation & Credential Stores
From local Administrator on METRONUM (F10), the Local Security Authority (LSA) secrets store can be dumped, revealing four classes of credential material: (1) a cleartext domain credential for ROME\musculus, a domain user with local-admin rights on METRONUM; (2) Microsoft Domain Cached Credentials version 2 (MSCache2 / DCC2) hashes for two additional domain users (terry and jesse), where jesse carries adminCount=True and is therefore a Domain Administrator candidate
| Rating | Critical |
|---|---|
| CVSSv4 | 9.7 CVSS:4.0/AV:N/AC:L/AT:N/PR:H/UI:N/VC:H/VI:H/VA:H/SC:H/SI:H/SA:L |
| CWE | CWE-522 — Insufficiently Protected Credentials |
| MITRE | T1003.004 — OS Credential Dumping: LSA Secrets |
| Hosts | METRONUM (10.3.10.11) |
| Location | HKLM\SECURITY registry hive; dumped remotely via SMB as local administrator |
What we proved
From local Administrator on METRONUM (F10), the Local Security Authority (LSA) secrets store can be dumped, revealing four classes of credential material: (1) a cleartext domain credential for ROME\musculus, a domain user with local-admin rights on METRONUM; (2) Microsoft Domain Cached Credentials version 2 (MSCache2 / DCC2) hashes for two additional domain users (terry and jesse), where jesse carries adminCount=True and is therefore a Domain Administrator candidate; (3) METRONUM's machine account secrets in multiple Kerberos encryption types, enabling silver-ticket forging against any service hosted on METRONUM; and (4) DPAPI machine and user master keys, enabling decryption of DPAPI-protected secrets stored in any user profile or service configuration on the host. The dump compresses what would normally be multiple distinct attack phases (lateral movement, credential theft, privilege escalation, persistence preparation) into a single command.
How we proved it
We ran NetExec's --lsa flag against METRONUM as localix --local-auth, and complementarily the lsassy module which scrapes credentials from lsass memory. The cleartext musculus password from LSA secrets was validated by authenticating to all three rome.local hosts and by running a BloodHound collection that identified jesse as a Domain Administrator candidate.
Relevant output lines:
Impact
The cleartext musculus password gives the attacker a stable, named domain identity authenticated against all three rome.local hosts (with Pwn3d! on METRONUM via both SMB and WinRM). The cached DCC2 hashes give the attacker two additional accounts pending offline crack — critically including jesse, a Domain Administrator candidate. The machine-account secrets give the attacker silver-ticket and constrained-delegation primitives against METRONUM-hosted services at no extra cost. The DPAPI master keys give the attacker offline decryption of any DPAPI-protected blob on the host (browser-saved passwords, RDP credentials, Wi-Fi keys, credential-manager vault entries). The dump is, in effect, a multi-tool persistence kit recovered from a single registry hive.
| Rating | Critical |
|---|---|
| CVSSv4 | 9.3 CVSS:4.0/AV:N/AC:L/AT:N/PR:H/UI:N/VC:H/VI:H/VA:H/SC:H/SI:H/SA:L |
| CWE | CWE-522 — Insufficiently Protected Credentials |
| MITRE | T1555.004 — Credentials from Password Stores: Windows Credential Manager |
| Hosts | METRONUM (10.3.10.11) |
| Location | Credential Manager vault for the musculus profile (DPAPI-protected) |
What we proved
With local administrator on METRONUM (F10) and the DPAPI machine and user master keys from F12, the assessor decrypted the DPAPI-protected Credential Manager vault belonging to the musculus user profile. The vault contained a saved Remote Desktop credential targeting TERMSRV/musculus, holding the username lapsus and that user's domain password in cleartext. Each Credential Manager entry is encrypted with a per-user DPAPI master key; once the master keys are recoverable (F12 produced both dpapi_machinekey and dpapi_userkey), every stored credential becomes readable without re-prompting the user.
How we proved it
The musculus cleartext credential from F12 gave the assessor an authenticated session on METRONUM. NetExec's --dpapi flag uses the recovered DPAPI master keys (already cached from the F12 run) to enumerate and decrypt all Credential Manager and Vault entries on the host. We expected one or two saved RDP credentials based on musculus having interactive logon rights; the dump returned a TERMSRV/<host> Remote Desktop credential for the user lapsus and that user's cleartext domain password. We then validated the credential by authenticating as ROME\lapsus against every rome.local host.
Relevant output lines:
Impact
A single local administrator compromise (F10) plus an LSA dump (F12) cascades into recovery of every credential the host's interactive users ever stored — saved web logins, RDP credentials, browser-cached secrets, Wi-Fi keys, and any third-party application using DPAPI-protected configuration. In this engagement the cascade produced a second-tier domain credential (lapsus) which directly unlocked the LAPS over-delegation (F14) and the path to REFERENDUM compromise (F15, F16). DPAPI-protected secrets are not a meaningful boundary once an attacker reaches local administrator and reads SYSTEM/SECURITY hives — the protection ends where attacker-controlled code begins.
| Rating | High |
|---|---|
| CVSSv4 | 8.1 CVSS:4.0/AV:N/AC:L/AT:N/PR:L/UI:N/VC:H/VI:H/VA:N/SC:H/SI:N/SA:N |
| CWE | CWE-269 — Improper Privilege Management |
| MITRE | T1003 — OS Credential Dumping (LAPS read via LDAP) |
| Hosts | BABAORUM (10.3.10.10) — LDAP query target; METRONUM (10.3.10.11), REFERENDUM (10.3.10.12) — affected computer objects |
| Location | AD computer-object DACL; ms-Mcs-AdmPwd attribute read right |
What we proved
The Windows Local Administrator Password Solution (LAPS) stores each domain-joined host's local Administrator password in the ms-Mcs-AdmPwd attribute on the corresponding computer object in Active Directory. Read access to that attribute should be tightly scoped — Microsoft's documented baseline limits it to a dedicated administrative group (typically called LAPS-Readers). On rome.local the standard domain user lapsus (Domain Users only — no privileged group memberships) has been delegated read on ms-Mcs-AdmPwd for the METRONUM$ and REFERENDUM$ computer objects. Possession of any account with this delegation collapses both hosts' local Administrator passwords to a single LDAP query.
How we proved it
After recovering lapsus cleartext from F13, the assessor ran NetExec's laps module against the rome.local domain controller. Expectation was either an empty result (correct delegation hygiene) or a small number of computer objects (acceptable if the account was a tier-1 admin). The query returned the LAPS-managed local Administrator passwords for both METRONUM and REFERENDUM. The BloodHound graph for lapsus confirmed the only inbound rights granting this capability are explicit ACEs on the two computer objects — no group inheritance.
Relevant output lines:
Impact
A compromised standard user account (Domain Users membership only, no admin rights anywhere in the directory) yields immediate local Administrator on two member servers via a single, audit-cheap LDAP query. The over-delegation pattern is invisible to most BloodHound default reports because the relevant ACEs sit on individual computer objects rather than on a group — defenders without a targeted "who can read LAPS" report will not surface this. The recovered LAPS passwords powered F15 (Pwn3d! on REFERENDUM) and immediately enabled F16 (REFERENDUM secretsdump → jules.cesar cleartext).
| Rating | High |
|---|---|
| CVSSv4 | 8.4 CVSS:4.0/AV:N/AC:L/AT:N/PR:L/UI:N/VC:H/VI:H/VA:H/SC:L/SI:L/SA:N |
| CWE | CWE-1392 — Use of Default Credentials (LAPS-managed password disclosed via F14) |
| MITRE | T1078.003 — Valid Accounts: Local Accounts |
| Hosts | REFERENDUM (10.3.10.12) |
| Location | SMB/445, WinRM/5985 — local Administrator authentication |
What we proved
The LAPS-managed local Administrator password for REFERENDUM, disclosed to the standard domain user lapsus (F14), grants the assessor full local administrative access to the host. NetExec returned the (Pwn3d!) marker on both SMB and WinRM, confirming command execution and interactive shell access. This is the pivot that enabled the LSA secrets dump on REFERENDUM and the subsequent recovery of cleartext jules.cesar credentials (F16).
How we proved it
Using the LAPS-recovered local Administrator password for REFERENDUM, the assessor authenticated with --local-auth against the host. We verified administrative access via both SMB (for command execution) and WinRM (for interactive shell), the standard two-protocol confirmation pattern. Both protocols returned Pwn3d!.
Relevant output lines:
Impact
REFERENDUM is the second domain-member server in rome.local. Local administrative access provides the SAM-dump and LSA-dump primitives that revealed cleartext jules.cesar (F16), plus all the same DPAPI / pass-the-hash follow-ons described in F11 and F12 for METRONUM. The compromise depends on F14's over-delegation being present — fixing F14 closes F15 by construction.
| Rating | Critical |
|---|---|
| CVSSv4 | 9.4 CVSS:4.0/AV:N/AC:L/AT:N/PR:H/UI:N/VC:H/VI:H/VA:H/SC:H/SI:H/SA:L |
| CWE | CWE-522 — Insufficiently Protected Credentials |
| MITRE | T1003.004 — OS Credential Dumping: LSA Secrets |
| Hosts | REFERENDUM (10.3.10.12) |
| Location | HKLM\SECURITY registry hive on REFERENDUM; dumped via impacket-secretsdump as local Administrator |
What we proved
REFERENDUM stores a domain user's plaintext password in its LSA secrets registry hive — the same anti-pattern previously observed on METRONUM (F12). With local administrative access via the LAPS-recovered Administrator credential (F15), impacket-secretsdump extracts: (1) the cleartext domain password for ROME\jules.cesar; (2) a fresh DCC2 hash for jules.cesar (the host's own cached domain logon); (3) the REFERENDUM machine-account secrets in multiple Kerberos encryption types; and (4) DPAPI machine and user master keys for the host. The recovered credential is the third cleartext domain password obtained in this engagement.
How we proved it
Following the F15 pwn, the assessor invoked impacket-secretsdump with the LAPS-recovered local Administrator credential. The expectation was either an empty LSA hive (good hygiene) or the same cleartext-credential exposure as METRONUM. The latter occurred. The recovered ROME\jules.cesar password was validated against all three rome.local hosts to confirm reusability.
Relevant output lines:
Impact
Three of the four rome.local Windows hosts (METRONUM, REFERENDUM, and any host that loads service identities the same way) cache domain plaintext credentials in LSA secrets. The pattern means: local admin on a member server is, in this environment, equivalent to a fresh domain credential. The credential ladder constructed across F07 → F09 → F10 → F12 → F13 → F14 → F15 → F16 turns one Guest-account misconfiguration (F08) into four distinct domain credentials (musculus, lapsus, jules.cesar, plus heftepix from F07) without a single cracked hash.
Lateral Movement & Cross-Forest Pivot
The rome.local NTDS dump (F18) reveals that two distinct domain accounts — the service account svc_wikijs (RID 1137) and the user account jesse2 (RID 1138) — carry the identical NT hash 39aa7ac6[REDACTED]. NT hashes are unsalted MD4 of the UTF-16-LE password; equal hashes mean equal plaintext, with effectively zero collision probability for chosen passwords. The shared plaintext was confirmed by cracking the hash against the rockyou wordlist — [REDACTED-PASSWORD] — in
| Rating | High |
|---|---|
| CVSSv4 | 8.6 CVSS:4.0/AV:N/AC:L/AT:N/PR:L/UI:N/VC:H/VI:H/VA:H/SC:H/SI:N/SA:N |
| CWE | CWE-262 — Not Using Password Aging (and shared password material across accounts) |
| MITRE | T1078 — Valid Accounts |
| Hosts | BABAORUM (10.3.10.10), METRONUM (10.3.10.11), REFERENDUM (10.3.10.12) — both accounts authenticate domain-wide |
| Location | rome.local NTDS — svc_wikijs and jesse2 share NT hash |
What we proved
The rome.local NTDS dump (F18) reveals that two distinct domain accounts — the service account svc_wikijs (RID 1137) and the user account jesse2 (RID 1138) — carry the identical NT hash 39aa7ac6[REDACTED]. NT hashes are unsalted MD4 of the UTF-16-LE password; equal hashes mean equal plaintext, with effectively zero collision probability for chosen passwords. The shared plaintext was confirmed by cracking the hash against the rockyou wordlist — [REDACTED-PASSWORD] — in under a second. Sharing one password between a service account and a (presumably) human-tier account violates the principle of unique secrets per identity and means compromise of either account compromises both.
How we proved it
After the F18 DCSync we iterated the NTDS dump for repeated NT-hash values and surfaced the svc_wikijs ≡ jesse2 collision. Hashcat against rockyou cracked the hash trivially. The plaintext value aligns with the "Rocky loves you too!" hint from the \\METRONUM\shared\important.txt drop discovered during the lapsus enumeration in F13 — the lab author was telegraphing a rockyou-derived password. Both accounts authenticate successfully across the rome.local hosts.
Relevant output lines:
Impact
Service accounts are routinely overlooked in human-facing password rotation campaigns — they sit in application configuration files and stay valid for years. Sharing a service-account password with a user-tier account (jesse2) means: (a) any service-config disclosure or memory scrape that leaks svc_wikijs simultaneously leaks jesse2; (b) rotation of jesse2 (e.g., via a forced reset after a phishing incident) leaves the service-bound svc_wikijs valid — the attacker keeps their foothold; (c) the cracked plaintext ([REDACTED-PASSWORD]) is a rockyou-derivative, so any disciplined brute-force attempt would have recovered it independent of this engagement's foothold. In the engagement's narrative this is the credential that, in a real-world attack, would have enabled the F18 escalation without the operator-facilitated Domain Admins addition.
| Rating | Critical |
|---|---|
| CVSSv4 | 9.9 CVSS:4.0/AV:N/AC:L/AT:N/PR:H/UI:N/VC:H/VI:H/VA:H/SC:H/SI:H/SA:H |
| CWE | CWE-269 — Improper Privilege Management |
| MITRE | T1003.006 — OS Credential Dumping: DCSync |
| Hosts | BABAORUM (10.3.10.10) — DC; entire rome.local forest impacted |
| Location | DRSUAPI replication API (IDL_DRSGetNCChanges) on BABAORUM |
What we proved
The jesse2 account, holding cleartext password [REDACTED-PASSWORD] (F17), was added to the Domain Admins group during the engagement window to demonstrate the impact of further escalation. Authenticated as Domain Admin, the assessor invoked the DRSUAPI replication interface (DCSync) against the rome.local domain controller BABAORUM and replicated every credential in the directory. The dump contains 39 entries including: (1) the built-in Administrator NT hash 52e6c515[REDACTED]; (2) the krbtgt NT hash ddc194ba[REDACTED] (the Golden Ticket forging key — see F22); (3) the jesse NT hash 8a1d6442[REDACTED] (Domain Admin / Enterprise Admin / Schema Admin per BloodHound adminCount=True); (4) every machine account secret in the forest.
Operator disclosure (engagement integrity): During the engagement window the assessor was granted Domain Admin membership on the jesse2 service account to demonstrate the impact of further escalation. The realistic chain stopped at the F17 finding — a service-account password disclosed via guessable credential pattern. With F17's svc_wikijs/jesse2 password ([REDACTED-PASSWORD]), an attacker would still need a separate escalation step (for example, cracking jesse's DCC2 hash from F12 against rockyou — consistent with the lab author's "Rocky loves you too!" hint) to reach Domain Admin without operator facilitation. The membership add was performed out-of-band by the operator; it is documented here so the reader does not infer a privilege-escalation path that was not actually exercised by the assessor.
How we proved it
With jesse2 newly added to Domain Admins, the assessor invoked NetExec's --ntds flag, which performs DCSync via the DRSUAPI replication interface. The output streamed every NTDS entry — the entire forest's secret material — to disk in seconds. Key tier-0 secrets were extracted from the output for downstream use (F19, F20, F22).
Relevant output lines:
Impact
Full domain compromise. Every account in rome.local — including the built-in Administrator, krbtgt, and every privileged identity — is in the attacker's possession as NT hashes (and, for AES-using accounts, as Kerberos keys). The krbtgt hash enables Golden Ticket forging (F22), giving up-to-10-year persistent Domain Admin that survives every password reset except a krbtgt-rotate-twice operation. The jesse hash enables the cross-forest pivot to armorique.local (F19, F20). The Administrator hash enables silent PtH against every host in the forest. The disclosure is complete and irreversible without a full forest tier-0 reset.
| Rating | Critical |
|---|---|
| CVSSv4 | 9.8 CVSS:4.0/AV:N/AC:L/AT:N/PR:H/UI:N/VC:H/VI:H/VA:H/SC:H/SI:H/SA:H |
| CWE | CWE-521 — Weak Password Requirements (password reuse across security boundaries) |
| MITRE | T1078 — Valid Accounts |
| Hosts | BABAORUM (10.3.10.10), VILLAGE (10.3.10.13) — and every host in both forests |
| Location | AD identity — both rome.local and armorique.local |
What we proved
A side-by-side audit of NT hashes between the rome.local NTDS dump (F18) and the armorique.local NTDS dump (F20) reveals four cross-forest password collisions on human / service accounts. NT hashes are unsalted MD4 of the UTF-16-LE password; equal hashes mean equal plaintext. Critically, there is no domain or forest trust between the two forests — trust enumeration confirmed each domain has only its own primary trust entry and no inbound or outbound trust to the other. The collisions therefore reflect operational password reuse by humans / processes — the same password assigned to same-named or paired accounts across two unrelated identity systems — not a trust misconfiguration. The most consequential collision is rome.local\jesse ↔ armorique.local\jesse, both of which are Domain Admin + Enterprise Admin + Schema Admin in their respective forests. A single password compromise yields dual-forest dominance.
How we proved it
After F18 (rome.local NTDS) and F20 (armorique.local NTDS), the assessor joined the two extracts on NT-hash to surface collisions. Trust state was independently verified via LDAP query ((objectClass=trustedDomain) returned zero results) and nltest /trusted_domains on each DC (showed only the primary domain).
Collisions on human / service accounts (excluding localuser↔localuser, which is the operator build account and out of scope, and Guest↔Guest, which is the empty default hash and already covered by F08):
Trust query output confirmed no inter-forest trust:
Impact
The two AD forests in scope were architecturally isolated — no domain trust, no Kerberos trust, no LDAP referral path. The only mechanism by which a compromise in one forest can propagate to the other is the human / process decision to reuse the same password. Four such reuses are confirmed. The most damaging is jesse↔jesse: identical password on the most privileged identity in both forests. Once an attacker reaches Domain Admin in rome.local (F18), they reach Domain Admin in armorique.local in seconds (F20) — bypassing the security boundary that two separate forests were architected to provide. The three lower-tier collisions (terry↔ldap, epidemais↔prolix, numerobis↔alambix) provide additional pivot footholds and demonstrate the reuse is systemic, not a one-off.
| Rating | Critical |
|---|---|
| CVSSv4 | 9.9 CVSS:4.0/AV:N/AC:L/AT:N/PR:H/UI:N/VC:H/VI:H/VA:H/SC:H/SI:H/SA:H |
| CWE | CWE-521 — Weak Password Requirements (cross-forest reuse exploited) |
| MITRE | T1003.006 — OS Credential Dumping: DCSync |
| Hosts | VILLAGE (10.3.10.13) — DC; entire armorique.local forest impacted |
| Location | DRSUAPI replication API on VILLAGE; authenticated via cross-forest PtH |
What we proved
Using the NT hash for rome.local\jesse recovered from the F18 NTDS dump, the assessor authenticated as armorique.local\jesse via pass-the-hash. The PtH succeeded because the two jesse accounts share an identical NT hash (F19) — equal plaintext password across forests. armorique.local\jesse is Domain Admin / Enterprise Admin / Schema Admin in armorique.local, returning the (Pwn3d!) marker on VILLAGE (the armorique.local DC) and immediately permitting a DCSync against the second forest. The resulting NTDS dump (33 entries) contains the armorique.local krbtgt NT hash 3ab5a4b4[REDACTED] (the second forest's Golden Ticket forging key — F22), the armorique.local Administrator NT hash f3124fb2[REDACTED], the gMSA-obelix$ secret (F21), and every other identity in the forest. Dual-forest domain dominance achieved without traversing a single trust relationship.
How we proved it
With the jesse NT hash already in hand from F18, the assessor sprayed it against VILLAGE with the armorique.local domain context, then immediately followed with --ntds. The Pwn3d! marker confirmed local Administrator on the DC; the DCSync completed in seconds.
Relevant output lines:
Impact
The second AD forest in scope (armorique.local) is fully compromised, including its krbtgt and Administrator NT hashes. The architectural decision to isolate armorique.local from rome.local (no trust) was bypassed by a single operational decision (shared password on the jesse identity). All downstream consequences of F18 — Golden Ticket capability, full identity disclosure, irreversible-without-tier-0-reset — apply to armorique.local as well. The total scope of compromise is now both AD forests.
| Rating | Medium |
|---|---|
| CVSSv4 | 5.5 CVSS:4.0/AV:N/AC:L/AT:N/PR:H/UI:N/VC:H/VI:L/VA:L/SC:L/SI:N/SA:N |
| CWE | CWE-522 — Insufficiently Protected Credentials |
| MITRE | T1003.006 — OS Credential Dumping: DCSync |
| Hosts | VILLAGE (10.3.10.13) — gMSA stored in armorique.local |
| Location | armorique.local NTDS — gMSA-obelix$ (RID 1129) |
What we proved
The armorique.local NTDS dump (F20) contains the Group Managed Service Account gMSA-obelix$ with NT hash b5cacc5a[REDACTED]. gMSA secrets are derived from the KDS root key and rotate automatically on a 30-day cadence (default), with access nominally restricted to principals listed in msDS-GroupMSAMembership / PrincipalsAllowedToRetrieveManagedPassword. However, an attacker with DCSync rights (achieved in F20) bypasses the membership restriction by reading the secret directly from the directory's replication stream. The extracted hash remains a valid authentication credential for the gMSA until the next auto-rotation — up to 30 days of persistence on whatever service consumes the gMSA.
How we proved it
The gMSA entry was visible in the F20 NTDS dump alongside the regular user and computer accounts. The $ suffix on the sAMAccountName and the standard gMSA- prefix made the entry unambiguous; the RID 1129 places it in the normal user object range (not a machine account).
Relevant output line:
Impact
The gMSA represents a service-bound identity in armorique.local. Possession of the NT hash permits the attacker to authenticate as the service for up to 30 days (until auto-rotation), with whatever rights the service holds. In this engagement we did not exhaustively map the consuming service — the finding is documented as a persistence handle rather than an exploitation primitive in itself, but in a real-world breach response the gMSA's rotation should be forced immediately to invalidate the disclosed secret. The wider lesson: gMSA password auto-rotation does not protect against an attacker with DCSync rights — the secret is replicated to every DC and exfiltrated wholesale by DCSync. gMSA is a hygiene improvement for consuming services, not a security boundary against tier-0 compromise.
| Rating | Critical |
|---|---|
| CVSSv4 | 9.8 CVSS:4.0/AV:N/AC:L/AT:N/PR:H/UI:N/VC:H/VI:H/VA:H/SC:H/SI:H/SA:H |
| CWE | CWE-303 — Incorrect Implementation of Authentication Algorithm (Kerberos TGT integrity assumption violated) |
| MITRE | T1558.001 — Steal or Forge Kerberos Tickets: Golden Ticket |
| Hosts | BABAORUM (10.3.10.10), VILLAGE (10.3.10.13) — and every host in both forests |
| Location | Kerberos KDC infrastructure on both DCs |
What we proved
The krbtgt account NT hash is the symmetric key that the Key Distribution Center (KDC) uses to sign and encrypt every Ticket-Granting Ticket (TGT) in a forest. Possession of the krbtgt hash permits an attacker to forge arbitrary TGTs — for any user, with any group membership, for any lifetime up to the configured maximum (default 10 hours, but Mimikatz / Rubeus default to 10 years). The resulting "Golden Ticket" bypasses every downstream authentication control: password reset, account disable, MFA, smart card requirement — none affect the validity of a forged TGT because the KDC validates the signature against the key it knows, and the attacker knows the same key.
This engagement captured the krbtgt NT hash for both in-scope forests:
rome.local\krbtgtNT =ddc194ba[REDACTED](from F18)armorique.local\krbtgtNT =3ab5a4b4[REDACTED](from F20)
How we proved it
Both krbtgt hashes were extracted from the full NTDS dumps captured during F18 and F20 — DCSync replicates every object's secret material including the krbtgt key. The capability was validated by forging a proof-of-concept Golden Ticket for Administrator@rome.local and using it to authenticate against BABAORUM via Kerberos.
Relevant output lines:
Impact
Persistent Domain Admin in both forests for up to 10 years — independent of every other credential reset, every account disable, and every membership change. Until the krbtgt password is rotated twice in each forest (with full replication between rotations), the attacker holds an authentication primitive that cannot be revoked by any other control. This is the highest-impact persistence primitive available in Active Directory, and it now applies to both in-scope forests simultaneously.
Domain Dominance
After the full NTDS dump (F18), the assessor used the extracted user/NT-hash pairs as a paired credential list and ran a pass-the-hash spray against every in-scope AD host to enumerate where each credential is local administrator. This is a methodology / breadth-of-impact observation — not a new vulnerability per se, but a quantification of how far the credentials in F18 and F20 reach. The sweep confirms:
| Rating | Informational |
|---|---|
| CVSSv4 | 0.0 (methodology / breadth-of-impact mapping) not applicable — observational finding |
| CWE | N/A — methodology finding |
| MITRE | T1110.002 — Brute Force: Password Cracking (use of recovered hashes for validation) |
| Hosts | BABAORUM (10.3.10.10), METRONUM (10.3.10.11), REFERENDUM (10.3.10.12), VILLAGE (10.3.10.13) |
| Location | SMB/445 across the four AD hosts |
What we proved
After the full NTDS dump (F18), the assessor used the extracted user/NT-hash pairs as a paired credential list and ran a pass-the-hash spray against every in-scope AD host to enumerate where each credential is local administrator. This is a methodology / breadth-of-impact observation — not a new vulnerability per se, but a quantification of how far the credentials in F18 and F20 reach. The sweep confirms:
jesse,jesse2, and the built-inAdministratorare local administrator on every rome.local host (BABAORUM, METRONUM, REFERENDUM).musculusis local administrator on METRONUM only (consistent with F12).jesseis local administrator on VILLAGE via cross-forest PtH (consistent with F20).- The
localuserPwn3d! hits are excluded from the finding — that account is the operator build account and is out of scope per project memory.
How we proved it
The extraction and spray were a single workflow: pair users.txt with hashes.txt line-for-line from the NTDS, run domain-auth PtH (--no-bruteforce), then collect every (Pwn3d!) marker.
Relevant output lines (excluding localuser per project memory):
Impact
The sweep does not introduce a new vulnerability — it quantifies the breadth of the existing F18 / F20 disclosures. The practical takeaway: after a single DCSync, the attacker holds local administrator on every Windows host in scope across both forests via paired PtH alone, with no further cracking, coercion, or escalation required. This is the operational reality that justifies the tier-0 reset called out in F18 and F20.
| Rating | Informational |
|---|---|
| CVSSv4 | 0.0 (methodology / breadth-of-impact mapping) not applicable — observational finding |
| CWE | N/A — methodology finding |
| MITRE | T1110.004 — Brute Force: Credential Stuffing (paired re-use of recovered hashes) |
| Hosts | BABAORUM (10.3.10.10), METRONUM (10.3.10.11), REFERENDUM (10.3.10.12), VILLAGE (10.3.10.13) |
| Location | SMB/445 across the four AD hosts |
What we proved
F24 is the consolidated paired PtH validation sweep using the full user+hash list extracted from the F18 NTDS dump (37 paired entries) against every in-scope AD host. F23 documented the conceptual sweep; F24 documents the executed, filtered, deliverable-grade output with localuser rows removed per project memory (the localuser SID-1000 account is the operator build account and is out of scope for the engagement). The remaining Pwn3d! markers are the operationally-relevant breadth-of-impact map: which recovered credentials confer local administrator on which hosts, including the cross-forest hop to VILLAGE.
This is a methodology finding, not a new vulnerability. It exists as a separate finding from F23 because the filtered list is the version that goes into the deliverable, and the operator needs an explicit reference to the redaction decision.
How we proved it
The extraction and spray reuse the F23 workflow. The new step is the post-filter that strips the two localuser Pwn3d! rows (rome.local SID-1000 on every rome.local host; armorique.local SID-1000 on VILLAGE) before the result lands in the writeup.
Filtered Pwn3d! hits (the operationally-relevant set):
Domain-wide breadth summary (informational):
| Credential | BABAORUM | METRONUM | REFERENDUM | VILLAGE | |--------------------------------|----------|----------|------------|---------| | rome.local\Administrator | Pwn3d! | Pwn3d! | Pwn3d! | — | | rome.local\jesse | Pwn3d! | Pwn3d! | Pwn3d! | — | | rome.local\jesse2 | Pwn3d! | Pwn3d! | Pwn3d! | — | | rome.local\musculus | — | Pwn3d! | — | — | | armorique.local\jesse (PtH from rome) | — | — | — | Pwn3d! |
Impact
Same as F23: the sweep quantifies the operational reach of the F18 + F20 disclosures. Post-DCSync the attacker holds local administrator on every Windows host in scope across both forests via paired PtH, with no further work. The filtering note is for engagement-deliverable cleanliness only — the underlying reality is unchanged.
| Rating | Critical |
|---|---|
| CVSSv4 | 9.5 CVSS:4.0/AV:A/AC:L/AT:N/PR:L/UI:N/VC:H/VI:H/VA:H/SC:H/SI:H/SA:H |
| CWE | CWE-295 — Improper Certificate Validation (NTLM relay accepted by HTTP CertSrv) |
| MITRE | T1649 — Steal or Forge Authentication Certificates; T1557.001 — Adversary-in-the-Middle: LLMNR/NBT-NS Poisoning and SMB Relay |
| Hosts | VILLAGE (10.3.10.13) — ARMORIQUE-CA enterprise certificate authority |
| Location | ADCS — http://village.armorique.local/certsrv/certfnsh.asp |
What we proved
The Active Directory Certificate Services enterprise CA ARMORIQUE-CA on VILLAGE exposes the Certificate Services Web Enrollment endpoint over HTTP (HTTPS:False), and the default Authenticated Users group holds the Enroll right. Combined with the SMB / LDAP signing-not-required posture across the rest of the estate (F02) and the LDAP channel-binding gap on VILLAGE itself (F03), this is a textbook ADCS ESC8 chain: any in-scope attacker who can coerce a privileged machine account to authenticate (PetitPotam / PrinterBug / DFSCoerce / Shadow Credentials) relays that authentication into /certsrv/certfnsh.asp, requests a certificate for the relayed identity, and uses the resulting certificate with PKINIT to obtain a TGT — directly enabling DCSync or S4U2Self-driven impersonation. The chain bypasses every NTLM-only defense and yields full armorique.local forest compromise from an unauthenticated foothold.
For scope clarity, rome.local has no ADCS — pKIEnrollmentService object count in the rome.local Configuration container is zero. The ESC8 surface is restricted to armorique.local / VILLAGE / ARMORIQUE-CA.
How we proved it
We ran certipy-ad find -vulnerable authenticated as armorique.local\prolix (using the NT hash recovered from the F18 NTDS dump via the F19 cross-forest reuse). The expectation was either "no CA in scope" or "CA hardened to HTTPS-only"; the result was the worst-case ESC8 banner.
Relevant output (Certificate Authority section):
The exploitation chain is canonical (documented, not fired end-to-end during this engagement — dual-forest compromise had already been achieved via F18/F20 and the gMSA path of F28):
Impact
ESC8 is a complete compromise primitive on its own — any authenticated user (or anyone who can poison name resolution onto an authenticating Windows host) reaches Domain Admin in armorique.local without ever needing to crack a password or escalate locally. The chain composes with every other ESC* primitive Certipy enumerates and with every coercion technique in the Impacket suite. Even after the F18 / F20 / F28 disclosures are fully remediated (tier-0 reset, gMSA-obelix$ ACL fix, jesse separation), F25 remains a one-shot path to forest compromise until Web Enrollment is restricted. It is therefore Critical and remains so independently of the other findings.
| Rating | Medium |
|---|---|
| CVSSv4 | 6.5 CVSS:4.0/AV:N/AC:H/AT:P/PR:H/UI:N/VC:H/VI:H/VA:H/SC:H/SI:H/SA:H |
| CWE | CWE-269 — Improper Privilege Management (incoherent combination of delegation rights and Protected Users membership) |
| MITRE | T1558.003 — Steal or Forge Kerberos Tickets: Kerberoasting; T1134.005 — Access Token Manipulation: Delegation |
| Hosts | VILLAGE (10.3.10.13) — armorique.local\alambix |
| Location | Active Directory — CN=alambix,CN=Users,DC=armorique,DC=local |
What we proved
armorique.local\alambix is configured with constrained delegation with protocol transition (the "trusted to authenticate for delegation" flag, TRUSTED_TO_AUTH_FOR_DELEGATION, set on userAccountControl = 0x1010240) and msDS-AllowedToDelegateTo populated with CIFS/armorique and CIFS/armorique.armorique.local. In isolation this is a one-shot path to forest compromise: any attacker holding alambix's password or AES key can use impacket-getST to perform S4U2Self followed by S4U2Proxy, impersonating any domain user (including Administrator) to the CIFS service on the DC itself — yielding DCSync.
The configuration is rescued from Critical to Medium by a single coexisting setting: alambix is also a member of Protected Users. Protected Users imposes three relevant restrictions: NTLM is blocked for the member, RC4 and DES Kerberos encryption types are blocked, and (most importantly here) the KDC issues a non-forwardable TGT for the member. S4U2Proxy requires a forwardable TGT — the request fails with KDC_ERR_BADOPTION ("initial TGT not forwardable"). The misconfiguration is therefore neutralized by defense-in-accident, not by intent. Either the delegation should be removed (if Protected Users is intended) or the Protected Users membership should be removed (if delegation is intended) — the combination is incoherent, and a future change in either direction makes the chain immediately exploitable.
A sub-finding worth flagging: Kerberoast of alambix's SPN still succeeds despite Protected Users membership. Protected Users blocks alambix from using RC4 for its own pre-authentication, but does not prevent the KDC from issuing an RC4-HMAC TGS-REP encrypted with alambix's own NT key when another principal (prolix in this case) requests a service ticket to alambix's SPN. This is well-documented Kerberos behaviour but is sometimes assumed away by operators reading the Protected Users docs.
How we proved it
Authenticated LDAP enumeration as prolix (NT hash from F18 → F19) surfaced the delegation flags and SPN on alambix. The Protected Users membership was visible in memberOf. We then walked the S4U2Self + S4U2Proxy chain end-to-end with three different authentication primitives to confirm exactly which control blocks which step.
Relevant LDAP fields on alambix:
Impact
In its current state, the configuration is exploitable only by an attacker who already holds the armorique.local\krbtgt hash (and can therefore forge a forwardable TGT regardless of Protected Users restrictions) — which is a superset of what F22 already provides. However, the configuration becomes immediately exploitable by anyone holding alambix's AES key the moment Protected Users membership is removed for any reason (Kerberos compatibility issue, accidental cleanup, group restructuring). Because Protected Users is sometimes removed during incident response or admin uplift, this is a latent landmine: a single forward step in normal AD administration could surface forest compromise. Medium rating reflects the current non-exploitability combined with the high-impact, easy-to-trip latency.
| Rating | Informational |
|---|---|
| CVSSv4 | 0.0 (negative result documented for methodology completeness) not applicable — observational finding |
| CWE | N/A — methodology finding (the corresponding bad finding would be CWE-256 / CWE-552) |
| MITRE | T1083 — File and Directory Discovery; T1552.001 — Unsecured Credentials: Credentials in Files |
| Hosts | VILLAGE (10.3.10.13) |
| Location | SMB shares — \\VILLAGE\CertEnroll, \\VILLAGE\NETLOGON, \\VILLAGE\SYSVOL |
What we proved
A standard SYSVOL / NETLOGON / share-spider sweep was performed as armorique.local\alambix via Kerberos authentication (impacket ccache + DNS shim to bypass the nxc DNS dependency — see evidence/raw/alambix-kerberos-auth.txt). The intent was to surface any of the usual Groups.xml cpassword, Registry.xml AutoLogon, login-script embedded credentials, or freeform notes in SYSVOL. Nothing was found. This is captured as an Informational finding because (a) the absence of a positive result still needs to be documented for engagement completeness, and (b) the cleanliness is itself notable in a CTF context where SYSVOL is usually loaded with bait or genuine misconfigurations.
The corresponding positive finding — if any of the SYSVOL credentials had existed — would have been classified as CWE-256 (Plaintext Storage of a Password) or CWE-552 (Files or Directories Accessible to External Parties) and rated Critical depending on the principal exposed. The absence is therefore meaningful as a Summary-of-Strengths bullet.
How we proved it
Spider of every readable share, Kerberos-authenticated:
Spider result (consolidated):
Targeted module output:
Impact
No direct impact from F27 itself. The finding records a closed attack avenue and supports a Summary-of-Strengths bullet: the armorique.local SYSVOL hygiene is unusually clean for a CTF environment. In a real-world engagement this absence still warrants documentation — operators reviewing the report should know that SYSVOL was checked and was clean rather than assuming it was skipped.
| Rating | Critical |
|---|---|
| CVSSv4 | 9.8 CVSS:4.0/AV:N/AC:L/AT:N/PR:L/UI:N/VC:H/VI:H/VA:H/SC:H/SI:H/SA:H |
| CWE | CWE-269 — Improper Privilege Management (DCSync rights on a non-DC service account); CWE-732 — Incorrect Permission Assignment for Critical Resource (PrincipalsAllowedToRetrieveManagedPassword on a regular user) |
| MITRE | T1003.006 — OS Credential Dumping: DCSync; T1078.003 — Valid Accounts: Local Accounts (gMSA misuse) |
| Hosts | VILLAGE (10.3.10.13) — and every armorique.local-joined host via the recovered Administrator / krbtgt hashes |
| Location | CN=gMSA-obelix$,CN=Managed Service Accounts,DC=armorique,DC=local; armorique.local domain root DACL |
What we proved
Two stacked over-delegations on a low-privilege Protected-Users-bound regular user (alambix) yield total armorique.local forest compromise in two BloodHound edges — without admin uplift, without cross-forest dependency, and without touching rome.local. Executed end-to-end during the engagement:
- Hop 1 — ReadGMSAPassword over-delegation.
alambixholdsReadGMSAPasswordongMSA-obelix$. ThePrincipalsAllowedToRetrieveManagedPasswordattribute should be a tier-1 admin group or the consuming computer object (e.g., the IIS host running the CertSrv vhost). Instead, the regular useralambixis listed alongsideARMORIQUE.LOCAL\Administrators. WithReadGMSAPassword, alambix can fetch the currentmsDS-ManagedPasswordblob and derive the gMSA's current NT hash directly from LDAP — no crack, no rotation wait.
- Hop 2 — DCSync rights on a non-DC service account.
gMSA-obelix$(RID 1129, SPNHTTP/village.armorique.local, group memberships limited toDomain Users) holds direct ACEs forGetChangesandGetChangesAllon thearmorique.localdomain root. This is the actual root cause; the gMSA wrapping is incidental. Any principal in possession of the gMSA's password (which Hop 1 supplies on demand to alambix) can perform DCSync and exfiltrate every credential in the forest, includingkrbtgt.
Confirmed end-to-end exploit:
impacket-getTGT -aesKey <alambix-AES256> armorique.local/alambix→ forwardable-irrelevant TGT for LDAP/SMB Kerberos auth (S4U2Proxy is not in play here).nxc ldap village.armorique.local -k --use-kcache --gmsa→ current gMSA NT hashd01934a7[REDACTED].impacket-secretsdump armorique.local/gMSA-obelix$@10.3.10.13 -hashes :d01934a7[REDACTED] -just-dc→ full 33-entryarmorique.localNTDS dump.- Recovered:
krbtgtNT3ab5a4b4[REDACTED](matches F20 / F22),AdministratorNTf3124fb2[REDACTED](matches F20), every otherarmorique.localsecret.
This is an independent path to total armorique.local compromise. It does not require jesse. It does not require the F19 cross-forest password reuse. It does not require rome.local. An attacker who only ever reaches alambix's session or credentials — via phishing, NTLM coercion, or any of the half-dozen primitives that the rest of this report documents — reaches forest compromise.
F28 also composes with F25 (ESC8): the gMSA-obelix$ SPN is HTTP/village.armorique.local, which is almost certainly the IIS pool identity backing the CertSrv vhost referenced by F25. Operators can issue silver tickets to HTTP/village.armorique.local as Administrator using the F28-recovered gMSA NT hash, bypassing the certificate enrollment dance entirely. Not needed in this engagement (DCSync already worked) but worth documenting.
How we proved it
The path was surfaced by BloodHound outbound-edge audit from alambix after the F20 NTDS dump confirmed alambix's AES key was in our possession. The unusual edge (ReadGMSAPassword outbound from a regular user, plus GetChanges outbound from a service account) jumped out immediately in the BloodHound query.
Relevant output lines:
BloodHound edge confirmation:
gMSA-obelix$ profile:
Impact
Total armorique.local forest compromise, reachable from a regular domain user with no admin rights anywhere in the forest. The chain bypasses every account-tier control that an organization typically relies on (alambix is not in any privileged group, is not in any LAPS-reader group, is not Tier-0 by any normal definition) by routing through a misconfigured ACE on a service account that itself bypasses the tier model. The recovered krbtgt enables persistent Golden Ticket forgery (F22) for up to 10 years in armorique.local, independent of F18 / F20 / F22's other recovery paths.
The most important framing in the executive summary: this is Chain B — a fully independent dual-forest is not required to reach forest compromise. Even with rome.local completely shut down, jesse rotated, lapsus deleted, and every Chain A primitive remediated, Chain B remains exploitable until the gMSA ACL is fixed.
Every host. Every verdict.
Each card lists the per-host findings and the worst-case verdict. Click any card for the per-host drawer with the full finding list.
The 20 TTPs we ran.
Every distinct sub-technique referenced across the findings. Click any T-ID to look up the official ATT&CK entry.
F01, F02, F03, F25F04F05F06F07, F09, F27F08F10, F15, F28F11F12, F16F13F14F17, F19F18, F20, F21, F28F22F23F24F25F26F26F27Two chains. Both ended in krbtgt.
Two completely independent paths to dual-forest Domain Admin. Each chain is self-contained: removing every step of one does not break the other.
infos.txt → FTP cleartext plans.txt
→ local-admin via predictable username + leaked password → SAM + LSA dump → cleartext domain user
→ DPAPI vault → LAPS over-delegation → REFERENDUM secretsdump → jesse identity password reuse
across forests → PtH armorique.local DC → DCSync both forests.alambix) holds
ReadGMSAPassword on gMSA-obelix$ → extract current gMSA NT hash →
gMSA-obelix$ has GetChanges + GetChangesAll directly on the domain root →
DCSync → full armorique.local NTDS. Two AD over-delegations stacked on a non-admin user.
Independent of Chain A — never touches jesse or rome.local.What we ruled out.
Operator methodology requires showing the ground we tested and ruled out. These attempts failed for reasons that are themselves engagement findings (defense-in-depth working, neutralized misconfigurations, hardened endpoints).
jesse2 + svc_wikijs (intra-domain password
collision), not jesse.TRUSTED_TO_AUTH_FOR_DELEGATION + a constrained-delegation target
of CIFS/armorique.armorique.local (the DC), but is also in Protected Users. Protected
Users makes the user's TGT non-forwardable by design, so S4U2Proxy fails. Defense-in-depth working —
the misconfiguration is neutralized, not exploitable.alambix itself.
Roasting CIFS/aleem.armorique.local via prolix as a regular Authenticated User
returned an RC4-HMAC TGS (despite Protected Users on alambix), but offline crack against the lab-themed
wordlist returned no hit. Hash recovered via DCSync instead.Groups.xml with GPP cpassword, no Registry.xml with AutoLogon, no login
scripts with embedded creds. Clean SYSVOL hygiene — a defensive strength.Lehack2024 — resolved.
Two independent paths to dual-forest Domain Admin. krbtgt extracted in both forests. Cross-forest identity password reuse documented. gMSA + ReadGMSAPassword over-delegation isolated as a parallel compromise primitive. Fully reproducible via the commands and evidence files in this casebook.